knitr::opts_chunk$set(echo = TRUE, warning = FALSE, message = FALSE, cache = FALSE)
Load packages
library(Matrix) # my pc needs this to load the tidyverse correctly
library(tidyverse) # tidy style coding
library(brms) # Bayesian models
library(loo) # to use information criteria in brms models
library(dagitty) # to build DAGs
library(ggdag) # to tidy DAGs
library(tidybayes) # Bayesian aesthetics
library(MetBrewer) # colours
library(kableExtra) # tables
library(patchwork) # putting plots together
library(DT) # for search- and saveable tables
library(pander) # for simpler tables
Supplementary methods
\(~\)
LH_m culturing
We maintained this LH_m stock in our laboratory for 32 generations
prior to creating the genotypes required for experimental evolution. We
cultured LH_m at 25C, with a 16-8 light-dark cycle and reared in vials
(95mm x 25mm) on a corn-meal, yeast and dextrose-based diet (recipe in
Table S1; ~8cm3 of food medium per vial) supplemented with dried yeast,
at a population size of at least 800 breeding individuals across 25
vials (16 flies of each sex per vial, following Rice et al. 2005). Each
generation begins by pooling the offspring produced across the 25 vials
and randomly assorting 16 female-male pairs to 25 new vials. We then
allow these breeding individuals 48 hours to interact and mate, before
transferring them to another set of new vials. After 24 hours of
egg-laying, we discard all adults, and allow juveniles 12 days to
compete for resources, pupate and eclose as adults. We then iteratively
repeat this process each generation to maintain the population.
Table S1. Recipe for food medium used in our
experiment. The provided quantities make ~ 1 litre of food.
tibble("Ingredients" = c("Soy flour", "Cornmeal", "Yeast", "Dextrose", "Agar", "Water", "Tegosept", "Acid mix (4 mL orthophosphoric acid, 41 mL propionic acid, 55 mL water to make 100 mL)"),
"Quantity" = c("20 g", "73 g", "35 g", "75 g", "6 g", "1000 mL", "17 mL", "14 mL")) %>%
pander(split.cell = 40, split.table = Inf)
| Soy flour |
20 g |
| Cornmeal |
73 g |
| Yeast |
35 g |
| Dextrose |
75 g |
| Agar |
6 g |
| Water |
1000 mL |
| Tegosept |
17 mL |
| Acid mix (4 mL orthophosphoric acid, 41 mL propionic
acid, 55 mL water to make 100 mL) |
14 mL |
\(~\)
Load in the data
\(~\)
fitness_data <- read_csv("data/SLC_fitness_data.csv") %>%
mutate(Fitness_vial_ID = as.factor(Fitness_vial_ID),
Block = as.factor(Block),
Population = as.factor(Population),
Treatment = as.factor(Treatment),
GFP = as.factor(GFP),
Sex = as.factor(Sex),
Rearing_vial = as.factor(Rearing_vial),
Total_red_offspring = Red_female_offspring + Red_male_offspring,
Total_bw_offspring = bw_female_offspring + bw_male_offspring,
Total_offspring = Total_red_offspring + Total_bw_offspring) %>%
rename(Inheritance_treatment = Treatment)
# Create a function to build HTML searchable tables
my_data_table <- function(df){
datatable(
df, rownames=FALSE,
autoHideNavigation = TRUE,
extensions = c("Scroller", "Buttons"),
options = list(
dom = 'Bfrtip',
deferRender=TRUE,
scrollX=TRUE, scrollY=400,
scrollCollapse=TRUE,
buttons =
list('pageLength', 'colvis', 'csv', list(
extend = 'pdf',
pageSize = 'A4',
orientation = 'landscape',
filename = 'fitness_data')),
pageLength = 692
)
)
}
my_data_table(fitness_data %>% select(-Comment))
Column explanations
Fitness_vial_ID: a unique identifier for each trial of the fitness
assay.
Block: the experiment was run in three distinct blocks, using flies
from separate generations.
Population: we measured the fitness of flies from 12 independent
populations that contained autosomes that had undergone experimental
evolution.
Inheritance_treatment: the populations carried autosomes that had
been exposed to one of three inheritance treatments for 20 generations:
a female-limited inheritance treatment where autosomes were always
passed from mother to daughter, a male-limited treatment where autosomes
were passed from father to son, and a control condition where
inheritance was unconstrained.
GFP: the GFP marker carried by the population. UBI indicates the
presence of a transgene that encodes ubiquitous expression of GFP, while
3xP indicates the presence of a different transgene that encodes the
expression of GFP in the ocelli.
Sex: the sex of the individuals that we were measuring the fitness
of.
Rearing_vial: the vial the treatment flies used in the trial
developed in. This variable is included to capture variation explained
by the rearing environment e.g. small differences in food moisture
content or quantity. Note that females and males can have the same
rearing vial as the sexes were reared together.
Red_female_offspring: the number of adult female offspring
sired/produced by flies sourced from one of the 12 populations.
Red_male_offspring: the number of adult male offspring sired/produced
by flies sourced from one of the 12 populations.
bw_female_offspring: the number of adult female offspring
sired/produced by the competitor flies in our fitness assay. bw
is a recessive allele that encodes brown eye colour.
bw_male_offspring: the number of adult male offspring sired/produced
by the competitor flies in our fitness assay. bw is a recessive
allele that encodes brown eye colour.
Total_red_offspring: the total number (sexes pooled) of adult
offspring sired/produced by flies sourced from one of the 12
populations.
Total_bw_offspring: the total number (sexes pooled) of adult
offspring sired/produced by competitor flies.
Total_offspring: the total number (sexes and eye colours pooled) of
adult offspring counted in each vial.
\(~\)
Modelling approach
\(~\)
Female and male fitness are fundamentally different concepts /
traits. There are also several differences between our female and male
fitness assays. The major difference is that the male assay contains
half the number of females in any given vial than does the female assay.
The logic behind this design choice is that sexually selected processes
are a more important determinant of male fitness than they are female
fitness, so any fitness differences may only be observed when
competition for fertilisations is high.
For these reasons, we choose to split the data up and model female
and male fitness separately.
female_fitness <-
fitness_data %>%
filter(Sex == "Female")
male_fitness <-
fitness_data %>%
filter(Sex == "Male") %>%
mutate(prop_red = Total_red_offspring / Total_offspring)
We fit the following fixed and random effects to model female and
male fitness. Our aim is to estimate the causal effect that
Inheritance_treatment (I) has on
fitness (F).
The DAG below shows our understanding of the scientific question we
are attempting to model. Arrows indicate the direction of causal
effects, at least as we interpret them.
# Lets make a function to speed up the DAG making process
gg_simple_dag <- function(d) {
d %>%
ggplot(aes(x = x, y = y, xend = xend, yend = yend)) +
geom_dag_point(color = met.brewer("Hiroshige")[4]) +
geom_dag_text(color = met.brewer("Hiroshige")[7]) +
geom_dag_edges() +
theme_dag()
}
dag_coords <-
tibble(name = c("I", "G", "B", "P", "R", "F"),
x = c(1, 1.5, 2.5, 1.5, 2.5, 2),
y = c(2, 3, 3, 1, 1, 2))
dagify(F ~ I + G + B + P + R,
coords = dag_coords) %>%
gg_simple_dag()

Fixed effects
Inheritance_treatment (I): this is the inheritance
regime that the autosomes carried by each of the populations were
subject to for 20 generations. There are three levels: populations
carrying female-adapted autosomes, populations containing male-adapted
autosomes and populations carrying control autosomes that experienced an
unmanipulated inheritance regime. We are designing our model to test for
a causal effect of this variable.
Mediator variables
Block (B): fitness might differ between the three
distinct blocks we split our experiment up into. Blocks differed
temporally, used flies from different generations and different batches
of food. It is also possible that there were minor fluctuations in the
lighting and temperature environment experienced during development
between blocks. Each of these variables may introduce variation into our
fitness measurements, that can be accounted for by including the
Block variable in our model.
GFP (G): it is possible that fitness may be affected by
the GFP transgene carried by each population. For example, one could
imagine that any unintended fitness effects of a transgene might be of
greater magnitude if it is expressed in a larger proportion of tissues,
as is the case for the UBI transgene versus the 3xP
transgene. Note that each GFP type is carried by an equal number of
populations from each of the three evolutionary treatments.
Varying/Random effects
Population (P): our design contained 12 independent
populations of autosomes that originated from a single outbred
laboratory fly population. The populations were split and autosomes from
each were subjected to one of the three evolution treatments for 20
generations. 4 populations experienced a female-limited inheritance
regime, 4 a male-limited regime and 4 an unlimited or control
regime.
Rearing_vial (R): the vial individual flies developed
within may introduce further variation into our response variable. Like
Block this variable controls for micro-environmental
variation.
\(~\)
Accounting for over-dispersion
The data is over-dispersed with several highly influential (outlier)
observations that have large effects on our posterior prediction. To
combat this, we fit models following the betabinomial
distribution family, as this is better equipped to deal with extreme
values at the tails i.e. overdispersion.
However, the beta-binomial is not a native family in
brms, we need to create the distribution family using the
custom_family() function. The code below is taken directly
from the brms_customfamilies vignette, which can be viewed
here.
beta_binomial2 <- custom_family(
"beta_binomial2", dpars = c("mu", "phi"),
links = c("logit", "log"), lb = c(NA, 2),
# note that we set the lower bound to 2, following McElreath, rather than Buerkner. This means that the most conservative estimate for phi we get is a flat expectation between 0 and 1
type = "int", vars = "vint1[n]"
)
stan_funs <- "
real beta_binomial2_lpmf(int y, real mu, real phi, int T) {
return beta_binomial_lpmf(y | T, mu * phi, (1 - mu) * phi);
}
int beta_binomial2_rng(real mu, real phi, int T) {
return beta_binomial_rng(T, mu * phi, (1 - mu) * phi);
}
"
stanvars <- stanvar(scode = stan_funs, block = "functions")
\(~\)
Female fitness
\(~\)
To estimate the fitness of females carrying each of the three
autosome types, we placed three experimental females into a yeasted vial
with three female competitors that carried the bw mutation. We
then introduced six males that also carried the bw mutation. We
allowed them to mate and oviposit for three days, then removed all
adults from the vial. 12 days later we counted all of the adult progeny
in the vial and scored them for eye-colour. Progeny with red eyes were
produced by the experimental females ( bw is recessive) and
progeny with brown eyes were produced by the competitor females. We
calculated fitness as the proportion of red eyed offspring in the
vial.
We present the fixed effects from the model:
\(~\)
female_fitness_model <-
brm(Total_red_offspring | vint(Total_offspring) ~ 1 + Inheritance_treatment + Block + GFP + (1|Population) + (1|Rearing_vial),
data = female_fitness, family = beta_binomial2,
prior = c(prior(normal(0, 1), class = Intercept),
prior(normal(0, 1.5), class = b),
prior(exponential(1), class = phi)),
iter = 4000, warmup = 2000, chains = 4, cores = 4,
control = list(adapt_delta = 0.95, max_treedepth = 10),
seed = 2, stanvars = stanvars, file = "Fits/female_fitness.model")
fixef(female_fitness_model) %>%
kable(digits = 3) %>%
kable_styling()
|
|
Estimate
|
Est.Error
|
Q2.5
|
Q97.5
|
|
Intercept
|
1.112
|
0.095
|
0.920
|
1.300
|
|
Inheritance_treatmentFemale_limited
|
0.168
|
0.104
|
-0.050
|
0.376
|
|
Inheritance_treatmentMale_limited
|
0.185
|
0.103
|
-0.018
|
0.388
|
|
Block2
|
-0.637
|
0.081
|
-0.793
|
-0.477
|
|
Block3
|
-0.624
|
0.072
|
-0.765
|
-0.483
|
|
GFPUBI
|
-0.322
|
0.085
|
-0.489
|
-0.154
|
We need to write some additional code to get some post processing
stuff i.e. LOO to work. Code courtesy of the
brms_customfamilies vignette, which can be viewed here.
Run LOO to see if we’ve effectively modelled over dispersion.
female_fitness_model <- add_criterion(female_fitness_model, criterion = "loo", file = "Fits/female_fitness.model")
loo(female_fitness_model)
##
## Computed from 8000 by 327 log-likelihood matrix
##
## Estimate SE
## elpd_loo -1399.9 10.6
## p_loo 23.0 2.1
## looic 2799.8 21.3
## ------
## Monte Carlo SE of elpd_loo is 0.1.
##
## Pareto k diagnostic values:
## Count Pct. Min. n_eff
## (-Inf, 0.5] (good) 326 99.7% 2845
## (0.5, 0.7] (ok) 1 0.3% 1130
## (0.7, 1] (bad) 0 0.0% <NA>
## (1, Inf) (very bad) 0 0.0% <NA>
##
## All Pareto k estimates are ok (k < 0.7).
## See help('pareto-k-diagnostic') for details.
The beta-binomial model looks good. It returns no points with high
pareto k values.
Conduct a posterior predictive check to confirm our model is doing
what we want it to.
pp_check(female_fitness_model, type = "hist", ndraws = 11, binwidth = 10) +
theme_minimal() +
theme(panel.background = element_blank())

The posterior predictive distribution matches our raw data quite
well, indicating the model is functioning as we wanted.
\(~\)
Derive predictions from the posterior
Get predictions from the model and present them in a Table
draws <- as_draws_df(female_fitness_model)
draws_female <-
draws %>%
mutate(`Female-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentFemale_limited),
`Male-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentMale_limited),
Control = inv_logit_scaled(b_Intercept)) %>%
select(`Female-limited`, Control, `Male-limited`) %>%
pivot_longer(cols = c(`Female-limited`, Control, `Male-limited`),
names_to = "Inheritance_treatment") %>%
rename(prop_focal_offspring = value) %>%
arrange(Inheritance_treatment)
draws_diff <- draws %>%
mutate(`Female-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentFemale_limited),
`Male-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentMale_limited),
Control = inv_logit_scaled(b_Intercept)) %>%
mutate(`Female - Control` = `Female-limited` - Control,
`Male - Control` = `Male-limited` - Control,
`Female - Male` = `Female-limited` - `Male-limited`) %>%
select(`Female - Control`, `Male - Control`, `Female - Male`)
#draws_diff %>%
# summarise(`Estimated prop. of offspring produced` = mean(`Male - Control`)*100,
# `2.5%` = quantile(`Male - Control`, probs = 0.025) *100,
# `97.5%` = quantile(`Male - Control`, probs = 0.975) *100)
draws_female %>%
group_by(Inheritance_treatment) %>%
summarise(`Estimated prop. of offspring produced` = mean(prop_focal_offspring),
`2.5%` = quantile(prop_focal_offspring, probs = 0.025),
`97.5%` = quantile(prop_focal_offspring, probs = 0.975)) %>%
pander(split.cell = 40, split.table = Inf, round = 3)
| Control |
0.752 |
0.715 |
0.786 |
| Female-limited |
0.782 |
0.747 |
0.812 |
| Male-limited |
0.785 |
0.753 |
0.814 |
# now find the differences between the control and the sex-limited treatments
# the inv_logit_scaled() function converts the posterior draws onto the response scale
prop_table_female <-
draws %>%
mutate(p_control = inv_logit_scaled(b_Intercept),
p_female = inv_logit_scaled(b_Inheritance_treatmentFemale_limited + b_Intercept),
p_male = inv_logit_scaled(b_Inheritance_treatmentMale_limited + b_Intercept),
`Female-limited` = p_female / p_control,
`Male-limited` = p_male / p_control) %>%
gather(key = `difference comparison`, value = `% difference`) %>%
filter(`difference comparison` == c("Female-limited", "Male-limited")) %>%
group_by(`difference comparison`) %>%
summarise(`Mean proportion of offspring produced relative to control` = mean(`% difference`),
`2.5%` = quantile(`% difference`, probs = 0.025),
`97.5%` = quantile(`% difference`, probs = 0.975)) %>%
rename(`Inheritance treatment` = `difference comparison`) #%>%
#pander(split.cell = 40, split.table = Inf, round = 3)
\(~\)
Male fitness
\(~\)
To estimate the fitness of males carrying each of the three
chromosome types, we conducted an experiment very similar to the female
fitness assay. However, because male fitness has stronger covariance
with fertilisation events than does female fitness, we conducted the
male fitness assay with a 1:2 sex ratio (female:male) rather than the
1:1 ratio used in the female assay. This increases the strength of
sexual selection and is a more appropriate way to expose differences in
fitness between groups of males. As with the females, we calculated
fitness as the proportion of red-eyed offspring in the vial.
male_fitness_model <-
brm(Total_red_offspring | vint(Total_offspring) ~ 1 + Inheritance_treatment + Block + GFP + (1|Population) + (1|Rearing_vial),
data = male_fitness, family = beta_binomial2,
prior = c(prior(normal(0, 1), class = Intercept),
prior(normal(0, 1.5), class = b),
prior(exponential(1), class = phi)),
iter = 4000, warmup = 2000, chains = 4, cores = 4,
control = list(adapt_delta = 0.95, max_treedepth = 10),
seed = 2, stanvars = stanvars, file = "Fits/male_fitness.model")
fixef(male_fitness_model) %>%
kable(digits = 3) %>%
kable_styling()
|
|
Estimate
|
Est.Error
|
Q2.5
|
Q97.5
|
|
Intercept
|
0.765
|
0.233
|
0.299
|
1.221
|
|
Inheritance_treatmentFemale_limited
|
0.417
|
0.268
|
-0.133
|
0.946
|
|
Inheritance_treatmentMale_limited
|
0.105
|
0.266
|
-0.430
|
0.631
|
|
Block2
|
0.970
|
0.149
|
0.670
|
1.265
|
|
Block3
|
-0.034
|
0.142
|
-0.304
|
0.247
|
|
GFPUBI
|
-0.336
|
0.226
|
-0.786
|
0.117
|
Run LOO to see if we’ve effectively modelled over dispersion.
male_fitness_model <- add_criterion(male_fitness_model, criterion = "loo", file = "Fits/male_fitness.model")
loo(male_fitness_model)
##
## Computed from 8000 by 360 log-likelihood matrix
##
## Estimate SE
## elpd_loo -1561.9 21.4
## p_loo 23.3 1.9
## looic 3123.8 42.8
## ------
## Monte Carlo SE of elpd_loo is NA.
##
## Pareto k diagnostic values:
## Count Pct. Min. n_eff
## (-Inf, 0.5] (good) 359 99.7% 2275
## (0.5, 0.7] (ok) 0 0.0% <NA>
## (0.7, 1] (bad) 0 0.0% <NA>
## (1, Inf) (very bad) 1 0.3% 4000
## See help('pareto-k-diagnostic') for details.
There is one point having a large effect on the posterior. Upon
inspection, this data point is not an unreasonable one and there is no
cause to remove it from the dataset. It also does not change the causal
effect of inheritance treatment on male fitness.
Conduct the posterior predictive check…
pp_check(male_fitness_model, type = "hist", ndraws = 11, binwidth = 10) +
theme_minimal() +
theme(panel.background = element_blank())

Derive estimates from posterior
Get predictions from the model and present them in a Table
# predictions for block 1, with UBI GFP
new_data <- tibble(Inheritance_treatment = male_fitness$Inheritance_treatment) %>%
distinct(Inheritance_treatment) %>%
mutate(Population = 1,
Block = 1,
Rearing_vial = 1,
GFP = "UBI",
Total_offspring = 1)
predictions_male <- fitted(male_fitness_model, newdata = new_data)
predictions_male <- cbind(new_data, predictions_male)
table1 <-
predictions_male %>%
select(-c(Population, Rearing_vial, GFP, Total_offspring)) %>%
arrange(Block) %>%
pander(split.cell = 40, split.table = Inf, round = 3)
draws_m <- as_draws_df(male_fitness_model)
# predictions averaged over mediator variables
draws_male <-
draws_m %>%
mutate(`Female-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentFemale_limited),
`Male-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentMale_limited),
Control = inv_logit_scaled(b_Intercept)) %>%
select(Control, `Female-limited`, `Male-limited`) %>%
pivot_longer(cols = c(Control, `Female-limited`, `Male-limited`),
names_to = "Inheritance_treatment") %>%
rename(prop_focal_offspring = value)
draws_diff_m <- draws_m %>%
mutate(`Female-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentFemale_limited),
`Male-limited` = inv_logit_scaled(b_Intercept + b_Inheritance_treatmentMale_limited),
Control = inv_logit_scaled(b_Intercept)) %>%
mutate(`Female - Control` = `Female-limited` - Control,
`Male - Control` = `Male-limited` - Control,
`Female - Male` = `Female-limited` - `Male-limited`) %>%
select(`Female - Control`, `Male - Control`, `Female - Male`)
# actual Table 1
draws_male %>%
group_by(Inheritance_treatment) %>%
summarise(`Estimated prop. of offspring sired` = mean(prop_focal_offspring),
`2.5%` = quantile(prop_focal_offspring, probs = 0.025),
`97.5%` = quantile(prop_focal_offspring, probs = 0.975)) %>%
pander(split.cell = 40, split.table = Inf, round = 3)
| Control |
0.68 |
0.574 |
0.772 |
| Female-limited |
0.762 |
0.662 |
0.841 |
| Male-limited |
0.702 |
0.594 |
0.794 |
# now find the differences between the control and the sex-limited Evolution_treatments
# the inv_logit_scaled() function converts the posterior draws onto the response scale
prop_table_male <-
draws_m %>%
mutate(p_control = inv_logit_scaled(b_Intercept),
p_female = inv_logit_scaled(b_Inheritance_treatmentFemale_limited + b_Intercept),
p_male = inv_logit_scaled(b_Inheritance_treatmentMale_limited + b_Intercept),
`Female-limited` = p_female / p_control,
`Male-limited` = p_male / p_control) %>%
gather(key = `difference comparison`, value = `% difference`) %>%
filter(`difference comparison` == c("Female-limited", "Male-limited")) %>%
group_by(`difference comparison`) %>%
summarise(`Mean proportion of offspring sired relative to control` = mean(`% difference`),
`2.5%` = quantile(`% difference`, probs = 0.025),
`97.5%` = quantile(`% difference`, probs = 0.975)) %>%
rename(`Inheritance treatment` = `difference comparison`) #%>%
#pander(split.cell = 40, split.table = Inf, round = 3)
Building Figure 2
# female plots
f_1 <-
draws_female %>%
mutate(Inheritance_treatment = fct_relevel(Inheritance_treatment, "Female-limited", "Control", "Male-limited")) %>%
ggplot(aes(Inheritance_treatment, prop_focal_offspring)) +
stat_halfeye(aes(fill = Inheritance_treatment), .width = c(0.66, 0.95), alpha = 1,
point_interval = "mean_qi", point_fill = "white",
shape = 21, point_size = 3, stroke = 1.5) + # width indicates the uncertainty intervals: we have 66% and 95% intervals
scale_fill_manual(values = met.brewer("Hiroshige", 3)) +
coord_flip() +
xlab("Inheritance treatment") +
ylab("Female fitness\n(prop. offspring produced)") +
theme_bw() +
theme(legend.position = "none",
panel.grid.minor = element_blank())
f_2 <-
draws_diff %>%
gather(key = parameter, value = `Fitness difference`) %>%
as_tibble() %>%
ggplot(aes(parameter, `Fitness difference`)) +
stat_halfeye(.width = c(0.66, 0.95), alpha = 0.9, point_interval = "mean_qi",
slab_fill = met.brewer("Hiroshige")[1],
shape = 21, point_size = 3, stroke = 1.5,
point_fill = "white") + # width indicates the uncertainty intervals: here we have 66% and 95% intervals
coord_flip() +
geom_hline(yintercept = 0, linetype = 2) +
#scale_y_continuous(breaks = c(, 0, 1)) +
xlab("Treatment contrast") +
ylab("Female fitness difference\n(prop. offspring produced)") +
theme_bw() +
theme(legend.position = "none",
panel.grid.minor = element_blank())
# male plots
f_3 <-
draws_male %>%
mutate(Inheritance_treatment = fct_relevel(Inheritance_treatment, "Female-limited", "Control", "Male-limited")) %>%
ggplot(aes(Inheritance_treatment, prop_focal_offspring)) +
stat_halfeye(aes(fill = Inheritance_treatment), .width = c(0.66, 0.95), alpha = 1,
point_interval = "mean_qi", point_fill = "white",
shape = 21, point_size = 3, stroke = 1.5) + # width indicates the uncertainty intervals: here we have 66% and 95% intervals
scale_fill_manual(values = met.brewer("Hiroshige", 3)) +
coord_flip() +
xlab("Inheritance treatment") +
ylab("Male fitness\n(prop. offspring produced)") +
theme_bw() +
theme(legend.position = "none",
panel.grid.minor = element_blank())
f_4 <-
draws_diff_m %>%
gather(key = parameter, value = `Fitness difference`) %>%
as_tibble() %>%
ggplot(aes(parameter, `Fitness difference`)) +
stat_halfeye(.width = c(0.66, 0.95), alpha = 0.9, point_interval = "mean_qi",
slab_fill = met.brewer("Hiroshige")[1],
shape = 21, point_size = 3, stroke = 1.5,
point_fill = "white") + # width indicates the uncertainty intervals: here we have 66% and 95% intervals
scale_fill_manual(values = met.brewer("Hokusai3", 3)) +
coord_flip() +
geom_hline(yintercept = 0, linetype = 2) +
scale_y_continuous(breaks = c(-0.2, -0.1, 0, 0.1, 0.2)) +
xlab("Treatment contrast") +
ylab("Male fitness difference\n(prop. offspring sired)") +
theme_bw() +
theme(legend.position = "none",
panel.grid.minor = element_blank())
(f_1 + f_2) /(f_3 + f_4) +
plot_annotation(tag_levels = 'a')

Figure 2: a shows the estimated
distribution of the mean for female fitness for flies carrying autosomes
that had previously experienced unconstrained inheritance (control),
female-limited inheritance or male-limited inheritance.
b shows the difference contrast in female fitness
between each of the three inheritance treatments. This difference is on
the proportion scale, where a value of 0.1 indicates that females of a
given inheritance treatment produce 10 more offspring per every 100 when
cohabiting with bw competitor females. c and
d depict the same things as a and
b, except for male fitness.
LS0tCnRpdGxlOiAiRXhwZXJpbWVudGFsIGVuZm9yY2VtZW50IG9mIHNleC1saW1pdGVkIGF1dG9zb21lIGluaGVyaXRhbmNlIGRvZXMgbm90IHJldmVhbCBpbnRyYWxvY3VzIHNleHVhbCBjb25mbGljdCIKYXV0aG9yOiAiVGhvbWFzIEtlYW5leSwgSGVpZGkgV29uZywgVGhlcmVzYSBKb25lcyBhbmQgTHVrZSBIb2xtYW4iCiNiaWJsaW9ncmFwaHk6ICJzdXBwX3JlZmVyZW5jZXMuYmliIgpvdXRwdXQ6CiAgaHRtbF9kb2N1bWVudDoKICAgIGNvZGVfZm9sZGluZzogaGlkZQogICAgZGVwdGg6IDEKICAgIG51bWJlcl9zZWN0aW9uczogbm8KICAgIHRoZW1lOiB5ZXRpCiAgICB0b2M6IHllcwogICAgdG9jX2Zsb2F0OiB5ZXMKICAgIGNvZGVfZG93bmxvYWQ6IHRydWUKZWRpdG9yX29wdGlvbnM6CiAgY2h1bmtfb3V0cHV0X3R5cGU6IGNvbnNvbGUKLS0tCgoKCmBgYHtyfQprbml0cjo6b3B0c19jaHVuayRzZXQoZWNobyA9IFRSVUUsIHdhcm5pbmcgPSBGQUxTRSwgbWVzc2FnZSA9IEZBTFNFLCBjYWNoZSA9IEZBTFNFKQpgYGAKCiMgTG9hZCBwYWNrYWdlcwoKYGBge3J9CmxpYnJhcnkoTWF0cml4KSAjIG15IHBjIG5lZWRzIHRoaXMgdG8gbG9hZCB0aGUgdGlkeXZlcnNlIGNvcnJlY3RseQpsaWJyYXJ5KHRpZHl2ZXJzZSkgIyB0aWR5IHN0eWxlIGNvZGluZwpsaWJyYXJ5KGJybXMpICMgQmF5ZXNpYW4gbW9kZWxzCmxpYnJhcnkobG9vKSAjIHRvIHVzZSBpbmZvcm1hdGlvbiBjcml0ZXJpYSBpbiBicm1zIG1vZGVscwpsaWJyYXJ5KGRhZ2l0dHkpICMgdG8gYnVpbGQgREFHcwpsaWJyYXJ5KGdnZGFnKSAjIHRvIHRpZHkgREFHcwpsaWJyYXJ5KHRpZHliYXllcykgIyBCYXllc2lhbiBhZXN0aGV0aWNzCmxpYnJhcnkoTWV0QnJld2VyKSAjIGNvbG91cnMKbGlicmFyeShrYWJsZUV4dHJhKSAjIHRhYmxlcwpsaWJyYXJ5KHBhdGNod29yaykgIyBwdXR0aW5nIHBsb3RzIHRvZ2V0aGVyCmxpYnJhcnkoRFQpICMgZm9yIHNlYXJjaC0gYW5kIHNhdmVhYmxlIHRhYmxlcwpsaWJyYXJ5KHBhbmRlcikgIyBmb3Igc2ltcGxlciB0YWJsZXMKCmBgYAoKIyBTdXBwbGVtZW50YXJ5IG1ldGhvZHMKCiR+JAoKKipMSF9tIGN1bHR1cmluZyoqCgpXZSBtYWludGFpbmVkIHRoaXMgTEhfbSBzdG9jayBpbiBvdXIgbGFib3JhdG9yeSBmb3IgMzIgZ2VuZXJhdGlvbnMgcHJpb3IgdG8gY3JlYXRpbmcgdGhlIGdlbm90eXBlcyByZXF1aXJlZCBmb3IgZXhwZXJpbWVudGFsIGV2b2x1dGlvbi4gV2UgY3VsdHVyZWQgTEhfbSBhdCAyNUMsIHdpdGggYSAxNi04IGxpZ2h0LWRhcmsgY3ljbGUgYW5kIHJlYXJlZCBpbiB2aWFscyAoOTVtbSB4IDI1bW0pIG9uIGEgY29ybi1tZWFsLCB5ZWFzdCBhbmQgZGV4dHJvc2UtYmFzZWQgZGlldCAocmVjaXBlIGluIFRhYmxlIFMxOyB+OGNtMyBvZiBmb29kIG1lZGl1bSBwZXIgdmlhbCkgc3VwcGxlbWVudGVkIHdpdGggZHJpZWQgeWVhc3QsIGF0IGEgcG9wdWxhdGlvbiBzaXplIG9mIGF0IGxlYXN0IDgwMCBicmVlZGluZyBpbmRpdmlkdWFscyBhY3Jvc3MgMjUgdmlhbHMgKDE2IGZsaWVzIG9mIGVhY2ggc2V4IHBlciB2aWFsLCBmb2xsb3dpbmcgUmljZSBldCBhbC4gMjAwNSkuIEVhY2ggZ2VuZXJhdGlvbiBiZWdpbnMgYnkgcG9vbGluZyB0aGUgb2Zmc3ByaW5nIHByb2R1Y2VkIGFjcm9zcyB0aGUgMjUgdmlhbHMgYW5kIHJhbmRvbWx5IGFzc29ydGluZyAxNiBmZW1hbGUtbWFsZSBwYWlycyB0byAyNSBuZXcgdmlhbHMuIFdlIHRoZW4gYWxsb3cgdGhlc2UgYnJlZWRpbmcgaW5kaXZpZHVhbHMgNDggaG91cnMgdG8gaW50ZXJhY3QgYW5kIG1hdGUsIGJlZm9yZSB0cmFuc2ZlcnJpbmcgdGhlbSB0byBhbm90aGVyIHNldCBvZiBuZXcgdmlhbHMuIEFmdGVyIDI0IGhvdXJzIG9mIGVnZy1sYXlpbmcsIHdlIGRpc2NhcmQgYWxsIGFkdWx0cywgYW5kIGFsbG93IGp1dmVuaWxlcyAxMiBkYXlzIHRvIGNvbXBldGUgZm9yIHJlc291cmNlcywgcHVwYXRlIGFuZCBlY2xvc2UgYXMgYWR1bHRzLiBXZSB0aGVuIGl0ZXJhdGl2ZWx5IHJlcGVhdCB0aGlzIHByb2Nlc3MgZWFjaCBnZW5lcmF0aW9uIHRvIG1haW50YWluIHRoZSBwb3B1bGF0aW9uLgoKKipUYWJsZSBTMSoqLiBSZWNpcGUgZm9yIGZvb2QgbWVkaXVtIHVzZWQgaW4gb3VyIGV4cGVyaW1lbnQuIFRoZSBwcm92aWRlZCBxdWFudGl0aWVzIG1ha2UgfiAxIGxpdHJlIG9mIGZvb2QuCgpgYGB7cn0KdGliYmxlKCJJbmdyZWRpZW50cyIgPSBjKCJTb3kgZmxvdXIiLCAiQ29ybm1lYWwiLCAiWWVhc3QiLCAiRGV4dHJvc2UiLCAiQWdhciIsICJXYXRlciIsICJUZWdvc2VwdCIsICJBY2lkIG1peCAoNCBtTCBvcnRob3Bob3NwaG9yaWMgYWNpZCwgNDEgbUwgcHJvcGlvbmljIGFjaWQsIDU1IG1MIHdhdGVyIHRvIG1ha2UgMTAwIG1MKSIpLAogICAgICAgIlF1YW50aXR5IiA9IGMoIjIwIGciLCAiNzMgZyIsICIzNSBnIiwgIjc1IGciLCAiNiBnIiwgIjEwMDAgbUwiLCAiMTcgbUwiLCAiMTQgbUwiKSkgJT4lIAogIHBhbmRlcihzcGxpdC5jZWxsID0gNDAsIHNwbGl0LnRhYmxlID0gSW5mKQpgYGAKCiR+JAoKIyBMb2FkIGluIHRoZSBkYXRhIAoKJH4kCgpgYGB7cn0KCmZpdG5lc3NfZGF0YSA8LSByZWFkX2NzdigiZGF0YS9TTENfZml0bmVzc19kYXRhLmNzdiIpICU+JSAKICBtdXRhdGUoRml0bmVzc192aWFsX0lEID0gYXMuZmFjdG9yKEZpdG5lc3NfdmlhbF9JRCksCiAgICAgICAgIEJsb2NrID0gYXMuZmFjdG9yKEJsb2NrKSwKICAgICAgICAgUG9wdWxhdGlvbiA9IGFzLmZhY3RvcihQb3B1bGF0aW9uKSwKICAgICAgICAgVHJlYXRtZW50ID0gYXMuZmFjdG9yKFRyZWF0bWVudCksCiAgICAgICAgIEdGUCA9IGFzLmZhY3RvcihHRlApLAogICAgICAgICBTZXggPSBhcy5mYWN0b3IoU2V4KSwKICAgICAgICAgUmVhcmluZ192aWFsID0gYXMuZmFjdG9yKFJlYXJpbmdfdmlhbCksCiAgICAgICAgIFRvdGFsX3JlZF9vZmZzcHJpbmcgPSBSZWRfZmVtYWxlX29mZnNwcmluZyArIFJlZF9tYWxlX29mZnNwcmluZywKICAgICAgICAgVG90YWxfYndfb2Zmc3ByaW5nID0gYndfZmVtYWxlX29mZnNwcmluZyArIGJ3X21hbGVfb2Zmc3ByaW5nLAogICAgICAgICBUb3RhbF9vZmZzcHJpbmcgPSBUb3RhbF9yZWRfb2Zmc3ByaW5nICsgVG90YWxfYndfb2Zmc3ByaW5nKSAlPiUgCiAgcmVuYW1lKEluaGVyaXRhbmNlX3RyZWF0bWVudCA9IFRyZWF0bWVudCkKCiMgQ3JlYXRlIGEgZnVuY3Rpb24gdG8gYnVpbGQgSFRNTCBzZWFyY2hhYmxlIHRhYmxlcwoKbXlfZGF0YV90YWJsZSA8LSBmdW5jdGlvbihkZil7CiAgZGF0YXRhYmxlKAogICAgZGYsIHJvd25hbWVzPUZBTFNFLAogICAgYXV0b0hpZGVOYXZpZ2F0aW9uID0gVFJVRSwKICAgIGV4dGVuc2lvbnMgPSBjKCJTY3JvbGxlciIsICAiQnV0dG9ucyIpLAogICAgb3B0aW9ucyA9IGxpc3QoCiAgICAgIGRvbSA9ICdCZnJ0aXAnLAogICAgICBkZWZlclJlbmRlcj1UUlVFLAogICAgICBzY3JvbGxYPVRSVUUsIHNjcm9sbFk9NDAwLAogICAgICBzY3JvbGxDb2xsYXBzZT1UUlVFLAogICAgICBidXR0b25zID0KICAgICAgICBsaXN0KCdwYWdlTGVuZ3RoJywgJ2NvbHZpcycsICdjc3YnLCBsaXN0KAogICAgICAgICAgZXh0ZW5kID0gJ3BkZicsCiAgICAgICAgICBwYWdlU2l6ZSA9ICdBNCcsCiAgICAgICAgICBvcmllbnRhdGlvbiA9ICdsYW5kc2NhcGUnLAogICAgICAgICAgZmlsZW5hbWUgPSAnZml0bmVzc19kYXRhJykpLAogICAgICBwYWdlTGVuZ3RoID0gNjkyCiAgICApCiAgKQp9CgoKbXlfZGF0YV90YWJsZShmaXRuZXNzX2RhdGEgJT4lIHNlbGVjdCgtQ29tbWVudCkpCgpgYGAKCioqQ29sdW1uIGV4cGxhbmF0aW9ucyoqCgpGaXRuZXNzX3ZpYWxfSUQ6IGEgdW5pcXVlIGlkZW50aWZpZXIgZm9yIGVhY2ggdHJpYWwgb2YgdGhlIGZpdG5lc3MgYXNzYXkuCgpCbG9jazogdGhlIGV4cGVyaW1lbnQgd2FzIHJ1biBpbiB0aHJlZSBkaXN0aW5jdCBibG9ja3MsIHVzaW5nIGZsaWVzIGZyb20gc2VwYXJhdGUgZ2VuZXJhdGlvbnMuCgpQb3B1bGF0aW9uOiB3ZSBtZWFzdXJlZCB0aGUgZml0bmVzcyBvZiBmbGllcyBmcm9tIDEyIGluZGVwZW5kZW50IHBvcHVsYXRpb25zIHRoYXQgY29udGFpbmVkIGF1dG9zb21lcyB0aGF0IGhhZCB1bmRlcmdvbmUgZXhwZXJpbWVudGFsIGV2b2x1dGlvbi4KCkluaGVyaXRhbmNlX3RyZWF0bWVudDogdGhlIHBvcHVsYXRpb25zIGNhcnJpZWQgYXV0b3NvbWVzIHRoYXQgaGFkIGJlZW4gZXhwb3NlZCB0byBvbmUgb2YgdGhyZWUgaW5oZXJpdGFuY2UgdHJlYXRtZW50cyBmb3IgMjAgZ2VuZXJhdGlvbnM6IGEgZmVtYWxlLWxpbWl0ZWQgaW5oZXJpdGFuY2UgdHJlYXRtZW50IHdoZXJlIGF1dG9zb21lcyB3ZXJlIGFsd2F5cyBwYXNzZWQgZnJvbSBtb3RoZXIgdG8gZGF1Z2h0ZXIsIGEgbWFsZS1saW1pdGVkIHRyZWF0bWVudCB3aGVyZSBhdXRvc29tZXMgd2VyZSBwYXNzZWQgZnJvbSBmYXRoZXIgdG8gc29uLCBhbmQgYSBjb250cm9sIGNvbmRpdGlvbiB3aGVyZSBpbmhlcml0YW5jZSB3YXMgdW5jb25zdHJhaW5lZC4KCkdGUDogdGhlIEdGUCBtYXJrZXIgY2FycmllZCBieSB0aGUgcG9wdWxhdGlvbi4gVUJJIGluZGljYXRlcyB0aGUgcHJlc2VuY2Ugb2YgYSB0cmFuc2dlbmUgdGhhdCBlbmNvZGVzIHViaXF1aXRvdXMgZXhwcmVzc2lvbiBvZiBHRlAsIHdoaWxlIDN4UCBpbmRpY2F0ZXMgdGhlIHByZXNlbmNlIG9mIGEgZGlmZmVyZW50IHRyYW5zZ2VuZSB0aGF0IGVuY29kZXMgdGhlIGV4cHJlc3Npb24gb2YgR0ZQIGluIHRoZSBvY2VsbGkuIAoKU2V4OiB0aGUgc2V4IG9mIHRoZSBpbmRpdmlkdWFscyB0aGF0IHdlIHdlcmUgbWVhc3VyaW5nIHRoZSBmaXRuZXNzIG9mLgoKUmVhcmluZ192aWFsOiB0aGUgdmlhbCB0aGUgdHJlYXRtZW50IGZsaWVzIHVzZWQgaW4gdGhlIHRyaWFsIGRldmVsb3BlZCBpbi4gVGhpcyB2YXJpYWJsZSBpcyBpbmNsdWRlZCB0byBjYXB0dXJlIHZhcmlhdGlvbiBleHBsYWluZWQgYnkgdGhlIHJlYXJpbmcgZW52aXJvbm1lbnQgZS5nLiBzbWFsbCBkaWZmZXJlbmNlcyBpbiBmb29kIG1vaXN0dXJlIGNvbnRlbnQgb3IgcXVhbnRpdHkuIE5vdGUgdGhhdCBmZW1hbGVzIGFuZCBtYWxlcyBjYW4gaGF2ZSB0aGUgc2FtZSByZWFyaW5nIHZpYWwgYXMgdGhlIHNleGVzIHdlcmUgcmVhcmVkIHRvZ2V0aGVyLgoKUmVkX2ZlbWFsZV9vZmZzcHJpbmc6IHRoZSBudW1iZXIgb2YgYWR1bHQgZmVtYWxlIG9mZnNwcmluZyBzaXJlZC9wcm9kdWNlZCBieSBmbGllcyBzb3VyY2VkIGZyb20gb25lIG9mIHRoZSAxMiBwb3B1bGF0aW9ucy4KClJlZF9tYWxlX29mZnNwcmluZzogdGhlIG51bWJlciBvZiBhZHVsdCBtYWxlIG9mZnNwcmluZyBzaXJlZC9wcm9kdWNlZCBieSBmbGllcyBzb3VyY2VkIGZyb20gb25lIG9mIHRoZSAxMiBwb3B1bGF0aW9ucy4KCmJ3X2ZlbWFsZV9vZmZzcHJpbmc6IHRoZSBudW1iZXIgb2YgYWR1bHQgZmVtYWxlIG9mZnNwcmluZyBzaXJlZC9wcm9kdWNlZCBieSB0aGUgY29tcGV0aXRvciBmbGllcyBpbiBvdXIgZml0bmVzcyBhc3NheS4gX2J3XyBpcyBhIHJlY2Vzc2l2ZSBhbGxlbGUgdGhhdCBlbmNvZGVzIGJyb3duIGV5ZSBjb2xvdXIuCgpid19tYWxlX29mZnNwcmluZzogdGhlIG51bWJlciBvZiBhZHVsdCBtYWxlIG9mZnNwcmluZyBzaXJlZC9wcm9kdWNlZCBieSB0aGUgY29tcGV0aXRvciBmbGllcyBpbiBvdXIgZml0bmVzcyBhc3NheS4gX2J3XyBpcyBhIHJlY2Vzc2l2ZSBhbGxlbGUgdGhhdCBlbmNvZGVzIGJyb3duIGV5ZSBjb2xvdXIuCgpUb3RhbF9yZWRfb2Zmc3ByaW5nOiB0aGUgdG90YWwgbnVtYmVyIChzZXhlcyBwb29sZWQpIG9mIGFkdWx0IG9mZnNwcmluZyBzaXJlZC9wcm9kdWNlZCBieSBmbGllcyBzb3VyY2VkIGZyb20gb25lIG9mIHRoZSAxMiBwb3B1bGF0aW9ucy4KClRvdGFsX2J3X29mZnNwcmluZzogdGhlIHRvdGFsIG51bWJlciAoc2V4ZXMgcG9vbGVkKSBvZiBhZHVsdCBvZmZzcHJpbmcgc2lyZWQvcHJvZHVjZWQgYnkgY29tcGV0aXRvciBmbGllcy4KClRvdGFsX29mZnNwcmluZzogdGhlIHRvdGFsIG51bWJlciAoc2V4ZXMgYW5kIGV5ZSBjb2xvdXJzIHBvb2xlZCkgb2YgYWR1bHQgb2Zmc3ByaW5nIGNvdW50ZWQgaW4gZWFjaCB2aWFsLgoKCiR+JAoKIyBNb2RlbGxpbmcgYXBwcm9hY2gKCiR+JAoKRmVtYWxlIGFuZCBtYWxlIGZpdG5lc3MgYXJlIGZ1bmRhbWVudGFsbHkgZGlmZmVyZW50IGNvbmNlcHRzIC8gdHJhaXRzLiBUaGVyZSBhcmUgYWxzbyBzZXZlcmFsIGRpZmZlcmVuY2VzIGJldHdlZW4gb3VyIGZlbWFsZSBhbmQgbWFsZSBmaXRuZXNzIGFzc2F5cy4gVGhlIG1ham9yIGRpZmZlcmVuY2UgaXMgdGhhdCB0aGUgbWFsZSBhc3NheSBjb250YWlucyBoYWxmIHRoZSBudW1iZXIgb2YgZmVtYWxlcyBpbiBhbnkgZ2l2ZW4gdmlhbCB0aGFuIGRvZXMgdGhlIGZlbWFsZSBhc3NheS4gVGhlIGxvZ2ljIGJlaGluZCB0aGlzIGRlc2lnbiBjaG9pY2UgaXMgdGhhdCBzZXh1YWxseSBzZWxlY3RlZCBwcm9jZXNzZXMgYXJlIGEgbW9yZSBpbXBvcnRhbnQgZGV0ZXJtaW5hbnQgb2YgbWFsZSBmaXRuZXNzIHRoYW4gdGhleSBhcmUgZmVtYWxlIGZpdG5lc3MsIHNvIGFueSBmaXRuZXNzIGRpZmZlcmVuY2VzIG1heSBvbmx5IGJlIG9ic2VydmVkIHdoZW4gY29tcGV0aXRpb24gZm9yIGZlcnRpbGlzYXRpb25zIGlzIGhpZ2guIAoKRm9yIHRoZXNlIHJlYXNvbnMsIHdlIGNob29zZSB0byBzcGxpdCB0aGUgZGF0YSB1cCBhbmQgbW9kZWwgZmVtYWxlIGFuZCBtYWxlIGZpdG5lc3Mgc2VwYXJhdGVseS4KCmBgYHtyfQpmZW1hbGVfZml0bmVzcyA8LSAKICBmaXRuZXNzX2RhdGEgJT4lCiAgZmlsdGVyKFNleCA9PSAiRmVtYWxlIikKCm1hbGVfZml0bmVzcyA8LSAKICBmaXRuZXNzX2RhdGEgJT4lCiAgZmlsdGVyKFNleCA9PSAiTWFsZSIpICU+JSAKICBtdXRhdGUocHJvcF9yZWQgPSBUb3RhbF9yZWRfb2Zmc3ByaW5nIC8gVG90YWxfb2Zmc3ByaW5nKQogIApgYGAKCldlIGZpdCB0aGUgZm9sbG93aW5nIGZpeGVkIGFuZCByYW5kb20gZWZmZWN0cyB0byBtb2RlbCBmZW1hbGUgYW5kIG1hbGUgZml0bmVzcy4gT3VyIGFpbSBpcyB0byBlc3RpbWF0ZSB0aGUgY2F1c2FsIGVmZmVjdCB0aGF0IGBJbmhlcml0YW5jZV90cmVhdG1lbnQgKEkpYCBoYXMgb24gYGZpdG5lc3MgKEYpYC4KClRoZSBEQUcgYmVsb3cgc2hvd3Mgb3VyIHVuZGVyc3RhbmRpbmcgb2YgdGhlIHNjaWVudGlmaWMgcXVlc3Rpb24gd2UgYXJlIGF0dGVtcHRpbmcgdG8gbW9kZWwuIEFycm93cyBpbmRpY2F0ZSB0aGUgZGlyZWN0aW9uIG9mIGNhdXNhbCBlZmZlY3RzLCBhdCBsZWFzdCBhcyB3ZSBpbnRlcnByZXQgdGhlbS4gCgpgYGB7cn0KIyBMZXRzIG1ha2UgYSBmdW5jdGlvbiB0byBzcGVlZCB1cCB0aGUgREFHIG1ha2luZyBwcm9jZXNzCgpnZ19zaW1wbGVfZGFnIDwtIGZ1bmN0aW9uKGQpIHsKICAKICBkICU+JSAKICAgIGdncGxvdChhZXMoeCA9IHgsIHkgPSB5LCB4ZW5kID0geGVuZCwgeWVuZCA9IHllbmQpKSArCiAgICBnZW9tX2RhZ19wb2ludChjb2xvciA9IG1ldC5icmV3ZXIoIkhpcm9zaGlnZSIpWzRdKSArCiAgICBnZW9tX2RhZ190ZXh0KGNvbG9yID0gbWV0LmJyZXdlcigiSGlyb3NoaWdlIilbN10pICsKICAgIGdlb21fZGFnX2VkZ2VzKCkgKyAKICAgIHRoZW1lX2RhZygpCiAgCn0KCmRhZ19jb29yZHMgPC0KICB0aWJibGUobmFtZSA9IGMoIkkiLCAiRyIsICJCIiwgIlAiLCAiUiIsICJGIiksCiAgICAgICAgIHggICAgPSBjKDEsIDEuNSwgMi41LCAxLjUsIDIuNSwgMiksCiAgICAgICAgIHkgICAgPSBjKDIsIDMsIDMsIDEsIDEsIDIpKQoKZGFnaWZ5KEYgfiBJICsgRyArIEIgKyBQICsgUiwKICAgICAgIGNvb3JkcyA9IGRhZ19jb29yZHMpICU+JQogIGdnX3NpbXBsZV9kYWcoKQoKCmBgYAoKKipGaXhlZCBlZmZlY3RzKioKCmBJbmhlcml0YW5jZV90cmVhdG1lbnQgKEkpYDogdGhpcyBpcyB0aGUgaW5oZXJpdGFuY2UgcmVnaW1lIHRoYXQgdGhlIGF1dG9zb21lcyBjYXJyaWVkIGJ5IGVhY2ggb2YgdGhlIHBvcHVsYXRpb25zIHdlcmUgc3ViamVjdCB0byBmb3IgMjAgZ2VuZXJhdGlvbnMuIFRoZXJlIGFyZSB0aHJlZSBsZXZlbHM6IHBvcHVsYXRpb25zIGNhcnJ5aW5nIGZlbWFsZS1hZGFwdGVkIGF1dG9zb21lcywgcG9wdWxhdGlvbnMgY29udGFpbmluZyBtYWxlLWFkYXB0ZWQgYXV0b3NvbWVzIGFuZCBwb3B1bGF0aW9ucyBjYXJyeWluZyBjb250cm9sIGF1dG9zb21lcyB0aGF0IGV4cGVyaWVuY2VkIGFuIHVubWFuaXB1bGF0ZWQgaW5oZXJpdGFuY2UgcmVnaW1lLiBXZSBhcmUgZGVzaWduaW5nIG91ciBtb2RlbCB0byB0ZXN0IGZvciBhIGNhdXNhbCBlZmZlY3Qgb2YgdGhpcyB2YXJpYWJsZS4KCl9NZWRpYXRvciB2YXJpYWJsZXNfCgpgQmxvY2sgKEIpYDogZml0bmVzcyBtaWdodCBkaWZmZXIgYmV0d2VlbiB0aGUgdGhyZWUgZGlzdGluY3QgYmxvY2tzIHdlIHNwbGl0IG91ciBleHBlcmltZW50IHVwIGludG8uIEJsb2NrcyBkaWZmZXJlZCB0ZW1wb3JhbGx5LCB1c2VkIGZsaWVzIGZyb20gZGlmZmVyZW50IGdlbmVyYXRpb25zIGFuZCBkaWZmZXJlbnQgYmF0Y2hlcyBvZiBmb29kLiBJdCBpcyBhbHNvIHBvc3NpYmxlIHRoYXQgdGhlcmUgd2VyZSBtaW5vciBmbHVjdHVhdGlvbnMgaW4gdGhlIGxpZ2h0aW5nIGFuZCB0ZW1wZXJhdHVyZSBlbnZpcm9ubWVudCBleHBlcmllbmNlZCBkdXJpbmcgZGV2ZWxvcG1lbnQgYmV0d2VlbiBibG9ja3MuIEVhY2ggb2YgdGhlc2UgdmFyaWFibGVzIG1heSBpbnRyb2R1Y2UgdmFyaWF0aW9uIGludG8gb3VyIGZpdG5lc3MgbWVhc3VyZW1lbnRzLCB0aGF0IGNhbiBiZSBhY2NvdW50ZWQgZm9yIGJ5IGluY2x1ZGluZyB0aGUgYEJsb2NrYCB2YXJpYWJsZSBpbiBvdXIgbW9kZWwuCgpgR0ZQIChHKWA6IGl0IGlzIHBvc3NpYmxlIHRoYXQgZml0bmVzcyBtYXkgYmUgYWZmZWN0ZWQgYnkgdGhlIEdGUCB0cmFuc2dlbmUgY2FycmllZCBieSBlYWNoIHBvcHVsYXRpb24uIEZvciBleGFtcGxlLCBvbmUgY291bGQgaW1hZ2luZSB0aGF0IGFueSB1bmludGVuZGVkIGZpdG5lc3MgZWZmZWN0cyBvZiBhIHRyYW5zZ2VuZSBtaWdodCBiZSBvZiBncmVhdGVyIG1hZ25pdHVkZSBpZiBpdCBpcyBleHByZXNzZWQgaW4gYSBsYXJnZXIgcHJvcG9ydGlvbiBvZiB0aXNzdWVzLCBhcyBpcyB0aGUgY2FzZSBmb3IgdGhlIF9VQklfIHRyYW5zZ2VuZSB2ZXJzdXMgdGhlIF8zeFBfIHRyYW5zZ2VuZS4gTm90ZSB0aGF0IGVhY2ggR0ZQIHR5cGUgaXMgY2FycmllZCBieSBhbiBlcXVhbCBudW1iZXIgb2YgcG9wdWxhdGlvbnMgZnJvbSBlYWNoIG9mIHRoZSB0aHJlZSBldm9sdXRpb25hcnkgdHJlYXRtZW50cy4KCioqVmFyeWluZy9SYW5kb20gZWZmZWN0cyoqCgpgUG9wdWxhdGlvbiAoUClgOiBvdXIgZGVzaWduIGNvbnRhaW5lZCAxMiBpbmRlcGVuZGVudCBwb3B1bGF0aW9ucyBvZiBhdXRvc29tZXMgdGhhdCBvcmlnaW5hdGVkIGZyb20gYSBzaW5nbGUgb3V0YnJlZCBsYWJvcmF0b3J5IGZseSBwb3B1bGF0aW9uLiBUaGUgcG9wdWxhdGlvbnMgd2VyZSBzcGxpdCBhbmQgYXV0b3NvbWVzIGZyb20gZWFjaCB3ZXJlIHN1YmplY3RlZCB0byBvbmUgb2YgdGhlIHRocmVlIGV2b2x1dGlvbiB0cmVhdG1lbnRzIGZvciAyMCBnZW5lcmF0aW9ucy4gNCBwb3B1bGF0aW9ucyBleHBlcmllbmNlZCBhIGZlbWFsZS1saW1pdGVkIGluaGVyaXRhbmNlIHJlZ2ltZSwgNCBhIG1hbGUtbGltaXRlZCByZWdpbWUgYW5kIDQgYW4gdW5saW1pdGVkIG9yIGNvbnRyb2wgcmVnaW1lLiAKCmBSZWFyaW5nX3ZpYWwgKFIpYDogdGhlIHZpYWwgaW5kaXZpZHVhbCBmbGllcyBkZXZlbG9wZWQgd2l0aGluIG1heSBpbnRyb2R1Y2UgZnVydGhlciB2YXJpYXRpb24gaW50byBvdXIgcmVzcG9uc2UgdmFyaWFibGUuIExpa2UgYEJsb2NrYCB0aGlzIHZhcmlhYmxlIGNvbnRyb2xzIGZvciBtaWNyby1lbnZpcm9ubWVudGFsIHZhcmlhdGlvbi4KCiR+JAoKKipBY2NvdW50aW5nIGZvciBvdmVyLWRpc3BlcnNpb24qKgoKVGhlIGRhdGEgaXMgb3Zlci1kaXNwZXJzZWQgd2l0aCBzZXZlcmFsIGhpZ2hseSBpbmZsdWVudGlhbCAob3V0bGllcikgb2JzZXJ2YXRpb25zIHRoYXQgaGF2ZSBsYXJnZSBlZmZlY3RzIG9uIG91ciBwb3N0ZXJpb3IgcHJlZGljdGlvbi4gVG8gY29tYmF0IHRoaXMsIHdlIGZpdCBtb2RlbHMgZm9sbG93aW5nIHRoZSBgYmV0YWJpbm9taWFsYCBkaXN0cmlidXRpb24gZmFtaWx5LCBhcyB0aGlzIGlzIGJldHRlciBlcXVpcHBlZCB0byBkZWFsIHdpdGggZXh0cmVtZSB2YWx1ZXMgYXQgdGhlIHRhaWxzIGkuZS4gb3ZlcmRpc3BlcnNpb24uCgpIb3dldmVyLCB0aGUgYmV0YS1iaW5vbWlhbCBpcyBub3QgYSBuYXRpdmUgZmFtaWx5IGluIGBicm1zYCwgd2UgbmVlZCB0byBjcmVhdGUgdGhlIGRpc3RyaWJ1dGlvbiBmYW1pbHkgdXNpbmcgdGhlIGBjdXN0b21fZmFtaWx5KClgIGZ1bmN0aW9uLiBUaGUgY29kZSBiZWxvdyBpcyB0YWtlbiBkaXJlY3RseSBmcm9tIHRoZSBgYnJtc19jdXN0b21mYW1pbGllc2AgdmlnbmV0dGUsIHdoaWNoIGNhbiBiZSB2aWV3ZWQgW2hlcmVdKGh0dHBzOi8vY3Jhbi5yLXByb2plY3Qub3JnL3dlYi9wYWNrYWdlcy9icm1zL3ZpZ25ldHRlcy9icm1zX2N1c3RvbWZhbWlsaWVzLmh0bWwpLgoKYGBge3J9CmJldGFfYmlub21pYWwyIDwtIGN1c3RvbV9mYW1pbHkoCiAgImJldGFfYmlub21pYWwyIiwgZHBhcnMgPSBjKCJtdSIsICJwaGkiKSwKICBsaW5rcyA9IGMoImxvZ2l0IiwgImxvZyIpLCBsYiA9IGMoTkEsIDIpLCAKICAjIG5vdGUgdGhhdCB3ZSBzZXQgdGhlIGxvd2VyIGJvdW5kIHRvIDIsIGZvbGxvd2luZyBNY0VscmVhdGgsIHJhdGhlciB0aGFuIEJ1ZXJrbmVyLiBUaGlzIG1lYW5zIHRoYXQgdGhlIG1vc3QgY29uc2VydmF0aXZlIGVzdGltYXRlIGZvciBwaGkgd2UgZ2V0IGlzIGEgZmxhdCBleHBlY3RhdGlvbiBiZXR3ZWVuIDAgYW5kIDEKICB0eXBlID0gImludCIsIHZhcnMgPSAidmludDFbbl0iCikKCgpzdGFuX2Z1bnMgPC0gIgogIHJlYWwgYmV0YV9iaW5vbWlhbDJfbHBtZihpbnQgeSwgcmVhbCBtdSwgcmVhbCBwaGksIGludCBUKSB7CiAgICByZXR1cm4gYmV0YV9iaW5vbWlhbF9scG1mKHkgfCBULCBtdSAqIHBoaSwgKDEgLSBtdSkgKiBwaGkpOwogIH0KICBpbnQgYmV0YV9iaW5vbWlhbDJfcm5nKHJlYWwgbXUsIHJlYWwgcGhpLCBpbnQgVCkgewogICAgcmV0dXJuIGJldGFfYmlub21pYWxfcm5nKFQsIG11ICogcGhpLCAoMSAtIG11KSAqIHBoaSk7CiAgfQoiCgpzdGFudmFycyA8LSBzdGFudmFyKHNjb2RlID0gc3Rhbl9mdW5zLCBibG9jayA9ICJmdW5jdGlvbnMiKQoKYGBgCgokfiQKCiMgRmVtYWxlIGZpdG5lc3MKCiR+JAoKVG8gZXN0aW1hdGUgdGhlIGZpdG5lc3Mgb2YgZmVtYWxlcyBjYXJyeWluZyBlYWNoIG9mIHRoZSB0aHJlZSBhdXRvc29tZSB0eXBlcywgd2UgcGxhY2VkIHRocmVlIGV4cGVyaW1lbnRhbCBmZW1hbGVzIGludG8gYSB5ZWFzdGVkIHZpYWwgd2l0aCB0aHJlZSBmZW1hbGUgY29tcGV0aXRvcnMgdGhhdCBjYXJyaWVkIHRoZSBfYndfIG11dGF0aW9uLiBXZSB0aGVuIGludHJvZHVjZWQgc2l4IG1hbGVzIHRoYXQgYWxzbyBjYXJyaWVkIHRoZSBfYndfIG11dGF0aW9uLiBXZSBhbGxvd2VkIHRoZW0gdG8gbWF0ZSBhbmQgb3ZpcG9zaXQgZm9yIHRocmVlIGRheXMsIHRoZW4gcmVtb3ZlZCBhbGwgYWR1bHRzIGZyb20gdGhlIHZpYWwuIDEyIGRheXMgbGF0ZXIgd2UgY291bnRlZCBhbGwgb2YgdGhlIGFkdWx0IHByb2dlbnkgaW4gdGhlIHZpYWwgYW5kIHNjb3JlZCB0aGVtIGZvciBleWUtY29sb3VyLiBQcm9nZW55IHdpdGggcmVkIGV5ZXMgd2VyZSBwcm9kdWNlZCBieSB0aGUgZXhwZXJpbWVudGFsIGZlbWFsZXMgKCBfYndfIGlzIHJlY2Vzc2l2ZSkgYW5kIHByb2dlbnkgd2l0aCBicm93biBleWVzIHdlcmUgcHJvZHVjZWQgYnkgdGhlIGNvbXBldGl0b3IgZmVtYWxlcy4gV2UgY2FsY3VsYXRlZCBmaXRuZXNzIGFzIHRoZSBwcm9wb3J0aW9uIG9mIHJlZCBleWVkIG9mZnNwcmluZyBpbiB0aGUgdmlhbC4gCgpXZSBwcmVzZW50IHRoZSBmaXhlZCBlZmZlY3RzIGZyb20gdGhlIG1vZGVsOgoKJH4kCgpgYGB7cn0KZmVtYWxlX2ZpdG5lc3NfbW9kZWwgPC0KICBicm0oVG90YWxfcmVkX29mZnNwcmluZyB8IHZpbnQoVG90YWxfb2Zmc3ByaW5nKSB+IDEgKyBJbmhlcml0YW5jZV90cmVhdG1lbnQgKyBCbG9jayArIEdGUCArICgxfFBvcHVsYXRpb24pICsgKDF8UmVhcmluZ192aWFsKSwKICAgICAgZGF0YSA9IGZlbWFsZV9maXRuZXNzLCBmYW1pbHkgPSBiZXRhX2Jpbm9taWFsMiwgCiAgICAgIHByaW9yID0gYyhwcmlvcihub3JtYWwoMCwgMSksIGNsYXNzID0gSW50ZXJjZXB0KSwKICAgICAgICAgICAgICAgIHByaW9yKG5vcm1hbCgwLCAxLjUpLCBjbGFzcyA9IGIpLAogICAgICAgICAgICAgICAgcHJpb3IoZXhwb25lbnRpYWwoMSksIGNsYXNzID0gcGhpKSksCiAgICAgIGl0ZXIgPSA0MDAwLCB3YXJtdXAgPSAyMDAwLCBjaGFpbnMgPSA0LCBjb3JlcyA9IDQsCiAgICAgIGNvbnRyb2wgPSBsaXN0KGFkYXB0X2RlbHRhID0gMC45NSwgbWF4X3RyZWVkZXB0aCA9IDEwKSwKICAgICAgc2VlZCA9IDIsIHN0YW52YXJzID0gc3RhbnZhcnMsIGZpbGUgPSAiRml0cy9mZW1hbGVfZml0bmVzcy5tb2RlbCIpCgpmaXhlZihmZW1hbGVfZml0bmVzc19tb2RlbCkgJT4lIAogIGthYmxlKGRpZ2l0cyA9IDMpICU+JSAKICBrYWJsZV9zdHlsaW5nKCkKCmBgYAoKV2UgbmVlZCB0byB3cml0ZSBzb21lIGFkZGl0aW9uYWwgY29kZSB0byBnZXQgc29tZSBwb3N0IHByb2Nlc3Npbmcgc3R1ZmYgaS5lLiBMT08gdG8gd29yay4gQ29kZSBjb3VydGVzeSBvZiB0aGUgYGJybXNfY3VzdG9tZmFtaWxpZXNgIHZpZ25ldHRlLCB3aGljaCBjYW4gYmUgdmlld2VkIFtoZXJlXShodHRwczovL2NyYW4uci1wcm9qZWN0Lm9yZy93ZWIvcGFja2FnZXMvYnJtcy92aWduZXR0ZXMvYnJtc19jdXN0b21mYW1pbGllcy5odG1sKS4KCmBgYHtyLCBpbmNsdWRlPUZBTFNFfQojIHdlIG5lZWQgdG8gd3JpdGUgc29tZSBhZGRpdGlvbmFsIGNvZGUgdG8gZ2V0IHNvbWUgcG9zdC1wcm9jZXNzaW5nIHN0dWZmIHRvIHdvcmsKCmV4cG9zZV9mdW5jdGlvbnMoZmVtYWxlX2ZpdG5lc3NfbW9kZWwsIHZlY3Rvcml6ZSA9IFRSVUUpCgoKbG9nX2xpa19iZXRhX2Jpbm9taWFsMiA8LSBmdW5jdGlvbihpLCBwcmVwKSB7CiAgbXUgPC0gYnJtczo6Z2V0X2RwYXIocHJlcCwgIm11IiwgaSA9IGkpCiAgcGhpIDwtIGJybXM6OmdldF9kcGFyKHByZXAsICJwaGkiLCBpID0gaSkKICB0cmlhbHMgPC0gcHJlcCRkYXRhJHZpbnQxW2ldCiAgeSA8LSBwcmVwJGRhdGEkWVtpXQogIGJldGFfYmlub21pYWwyX2xwbWYoeSwgbXUsIHBoaSwgdHJpYWxzKQp9Cgpwb3N0ZXJpb3JfcHJlZGljdF9iZXRhX2Jpbm9taWFsMiA8LSBmdW5jdGlvbihpLCBwcmVwLCAuLi4pIHsKICBtdSA8LSBicm1zOjpnZXRfZHBhcihwcmVwLCAibXUiLCBpID0gaSkKICBwaGkgPC0gYnJtczo6Z2V0X2RwYXIocHJlcCwgInBoaSIsIGkgPSBpKQogIHRyaWFscyA8LSBwcmVwJGRhdGEkdmludDFbaV0KICBiZXRhX2Jpbm9taWFsMl9ybmcobXUsIHBoaSwgdHJpYWxzKQp9Cgpwb3N0ZXJpb3JfZXByZWRfYmV0YV9iaW5vbWlhbDIgPC0gZnVuY3Rpb24ocHJlcCkgewogIG11IDwtIGJybXM6OmdldF9kcGFyKHByZXAsICJtdSIpCiAgdHJpYWxzIDwtIHByZXAkZGF0YSR2aW50MQogIHRyaWFscyA8LSBtYXRyaXgodHJpYWxzLCBucm93ID0gbnJvdyhtdSksIG5jb2wgPSBuY29sKG11KSwgYnlyb3cgPSBUUlVFKQogIG11ICogdHJpYWxzCn0KYGBgCgpSdW4gTE9PIHRvIHNlZSBpZiB3ZSd2ZSBlZmZlY3RpdmVseSBtb2RlbGxlZCBvdmVyIGRpc3BlcnNpb24uCgpgYGB7cn0KCmZlbWFsZV9maXRuZXNzX21vZGVsIDwtIGFkZF9jcml0ZXJpb24oZmVtYWxlX2ZpdG5lc3NfbW9kZWwsIGNyaXRlcmlvbiA9ICJsb28iLCBmaWxlID0gIkZpdHMvZmVtYWxlX2ZpdG5lc3MubW9kZWwiKQoKbG9vKGZlbWFsZV9maXRuZXNzX21vZGVsKQoKYGBgCgpUaGUgYmV0YS1iaW5vbWlhbCBtb2RlbCBsb29rcyBnb29kLiBJdCByZXR1cm5zIG5vIHBvaW50cyB3aXRoIGhpZ2ggcGFyZXRvIGsgdmFsdWVzLgoKQ29uZHVjdCBhIHBvc3RlcmlvciBwcmVkaWN0aXZlIGNoZWNrIHRvIGNvbmZpcm0gb3VyIG1vZGVsIGlzIGRvaW5nIHdoYXQgd2Ugd2FudCBpdCB0by4KCmBgYHtyfQpwcF9jaGVjayhmZW1hbGVfZml0bmVzc19tb2RlbCwgdHlwZSA9ICJoaXN0IiwgbmRyYXdzID0gMTEsIGJpbndpZHRoID0gMTApICsKICB0aGVtZV9taW5pbWFsKCkgKwogIHRoZW1lKHBhbmVsLmJhY2tncm91bmQgPSBlbGVtZW50X2JsYW5rKCkpCmBgYAoKVGhlIHBvc3RlcmlvciBwcmVkaWN0aXZlIGRpc3RyaWJ1dGlvbiBtYXRjaGVzIG91ciByYXcgZGF0YSBxdWl0ZSB3ZWxsLCBpbmRpY2F0aW5nIHRoZSBtb2RlbCBpcyBmdW5jdGlvbmluZyBhcyB3ZSB3YW50ZWQuCgokfiQKCiMjIERlcml2ZSBwcmVkaWN0aW9ucyBmcm9tIHRoZSBwb3N0ZXJpb3IKCkdldCBwcmVkaWN0aW9ucyBmcm9tIHRoZSBtb2RlbCBhbmQgcHJlc2VudCB0aGVtIGluIGEgVGFibGUKCmBgYHtyfQoKZHJhd3MgPC0gYXNfZHJhd3NfZGYoZmVtYWxlX2ZpdG5lc3NfbW9kZWwpCgpkcmF3c19mZW1hbGUgPC0KICBkcmF3cyAgJT4lIAogIG11dGF0ZShgRmVtYWxlLWxpbWl0ZWRgID0gaW52X2xvZ2l0X3NjYWxlZChiX0ludGVyY2VwdCArIGJfSW5oZXJpdGFuY2VfdHJlYXRtZW50RmVtYWxlX2xpbWl0ZWQpLAogICAgICAgICBgTWFsZS1saW1pdGVkYCA9IGludl9sb2dpdF9zY2FsZWQoYl9JbnRlcmNlcHQgKyBiX0luaGVyaXRhbmNlX3RyZWF0bWVudE1hbGVfbGltaXRlZCksCiAgICAgICAgIENvbnRyb2wgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0KSkgJT4lIAogIHNlbGVjdChgRmVtYWxlLWxpbWl0ZWRgLCBDb250cm9sLCBgTWFsZS1saW1pdGVkYCkgJT4lIAogICAgcGl2b3RfbG9uZ2VyKGNvbHMgPSBjKGBGZW1hbGUtbGltaXRlZGAsIENvbnRyb2wsIGBNYWxlLWxpbWl0ZWRgKSwKICAgICAgICAgICAgICAgICBuYW1lc190byA9ICJJbmhlcml0YW5jZV90cmVhdG1lbnQiKSAlPiUgCiAgcmVuYW1lKHByb3BfZm9jYWxfb2Zmc3ByaW5nID0gdmFsdWUpICU+JSAKICBhcnJhbmdlKEluaGVyaXRhbmNlX3RyZWF0bWVudCkKCmRyYXdzX2RpZmYgPC0gZHJhd3MgICU+JSAKICBtdXRhdGUoYEZlbWFsZS1saW1pdGVkYCA9IGludl9sb2dpdF9zY2FsZWQoYl9JbnRlcmNlcHQgKyBiX0luaGVyaXRhbmNlX3RyZWF0bWVudEZlbWFsZV9saW1pdGVkKSwKICAgICAgICAgYE1hbGUtbGltaXRlZGAgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0ICsgYl9Jbmhlcml0YW5jZV90cmVhdG1lbnRNYWxlX2xpbWl0ZWQpLAogICAgICAgICBDb250cm9sID0gaW52X2xvZ2l0X3NjYWxlZChiX0ludGVyY2VwdCkpICU+JQogIG11dGF0ZShgRmVtYWxlIC0gQ29udHJvbGAgPSBgRmVtYWxlLWxpbWl0ZWRgIC0gQ29udHJvbCwKICAgICAgICAgYE1hbGUgLSBDb250cm9sYCA9IGBNYWxlLWxpbWl0ZWRgIC0gQ29udHJvbCwKICAgICAgICAgYEZlbWFsZSAtIE1hbGVgID0gYEZlbWFsZS1saW1pdGVkYCAtIGBNYWxlLWxpbWl0ZWRgKSAlPiUgCiAgc2VsZWN0KGBGZW1hbGUgLSBDb250cm9sYCwgYE1hbGUgLSBDb250cm9sYCwgYEZlbWFsZSAtIE1hbGVgKQoKICNkcmF3c19kaWZmICU+JSAKICAjIHN1bW1hcmlzZShgRXN0aW1hdGVkIHByb3AuIG9mIG9mZnNwcmluZyBwcm9kdWNlZGAgPSBtZWFuKGBNYWxlIC0gQ29udHJvbGApKjEwMCwKICAgIyAgICAgICAgIGAyLjUlYCA9IHF1YW50aWxlKGBNYWxlIC0gQ29udHJvbGAsIHByb2JzID0gMC4wMjUpICoxMDAsCiAgICAjICAgICAgICBgOTcuNSVgID0gcXVhbnRpbGUoYE1hbGUgLSBDb250cm9sYCwgcHJvYnMgPSAwLjk3NSkgKjEwMCkKCmRyYXdzX2ZlbWFsZSAlPiUgCiAgZ3JvdXBfYnkoSW5oZXJpdGFuY2VfdHJlYXRtZW50KSAlPiUgCiAgc3VtbWFyaXNlKGBFc3RpbWF0ZWQgcHJvcC4gb2Ygb2Zmc3ByaW5nIHByb2R1Y2VkYCA9IG1lYW4ocHJvcF9mb2NhbF9vZmZzcHJpbmcpLAogICAgICAgICAgICBgMi41JWAgPSBxdWFudGlsZShwcm9wX2ZvY2FsX29mZnNwcmluZywgcHJvYnMgPSAwLjAyNSksCiAgICAgICAgICAgIGA5Ny41JWAgPSBxdWFudGlsZShwcm9wX2ZvY2FsX29mZnNwcmluZywgcHJvYnMgPSAwLjk3NSkpICU+JSAKICBwYW5kZXIoc3BsaXQuY2VsbCA9IDQwLCBzcGxpdC50YWJsZSA9IEluZiwgcm91bmQgPSAzKQoKIyBub3cgZmluZCB0aGUgZGlmZmVyZW5jZXMgYmV0d2VlbiB0aGUgY29udHJvbCBhbmQgdGhlIHNleC1saW1pdGVkIHRyZWF0bWVudHMKCiMgdGhlIGludl9sb2dpdF9zY2FsZWQoKSBmdW5jdGlvbiBjb252ZXJ0cyB0aGUgcG9zdGVyaW9yIGRyYXdzIG9udG8gdGhlIHJlc3BvbnNlIHNjYWxlIAoKcHJvcF90YWJsZV9mZW1hbGUgPC0KICBkcmF3cyAlPiUgCiAgbXV0YXRlKHBfY29udHJvbCA9ICBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0KSwKICAgICAgICAgcF9mZW1hbGUgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW5oZXJpdGFuY2VfdHJlYXRtZW50RmVtYWxlX2xpbWl0ZWQgKyBiX0ludGVyY2VwdCksCiAgICAgICAgIHBfbWFsZSA9IGludl9sb2dpdF9zY2FsZWQoYl9Jbmhlcml0YW5jZV90cmVhdG1lbnRNYWxlX2xpbWl0ZWQgKyBiX0ludGVyY2VwdCksCiAgICAgICAgIGBGZW1hbGUtbGltaXRlZGAgPSBwX2ZlbWFsZSAvIHBfY29udHJvbCwKICAgICAgICAgYE1hbGUtbGltaXRlZGAgPSBwX21hbGUgLyBwX2NvbnRyb2wpICU+JSAKICBnYXRoZXIoa2V5ID0gYGRpZmZlcmVuY2UgY29tcGFyaXNvbmAsIHZhbHVlID0gYCUgZGlmZmVyZW5jZWApICU+JSAKICBmaWx0ZXIoYGRpZmZlcmVuY2UgY29tcGFyaXNvbmAgPT0gYygiRmVtYWxlLWxpbWl0ZWQiLCAiTWFsZS1saW1pdGVkIikpICU+JSAKICBncm91cF9ieShgZGlmZmVyZW5jZSBjb21wYXJpc29uYCkgICU+JSAKICBzdW1tYXJpc2UoYE1lYW4gcHJvcG9ydGlvbiBvZiBvZmZzcHJpbmcgcHJvZHVjZWQgcmVsYXRpdmUgdG8gY29udHJvbGAgID0gbWVhbihgJSBkaWZmZXJlbmNlYCksCiAgICAgICAgICAgIGAyLjUlYCA9IHF1YW50aWxlKGAlIGRpZmZlcmVuY2VgLCBwcm9icyA9IDAuMDI1KSwKICAgICAgICAgICAgYDk3LjUlYCA9IHF1YW50aWxlKGAlIGRpZmZlcmVuY2VgLCBwcm9icyA9IDAuOTc1KSkgJT4lIAogIHJlbmFtZShgSW5oZXJpdGFuY2UgdHJlYXRtZW50YCA9IGBkaWZmZXJlbmNlIGNvbXBhcmlzb25gKSAjJT4lIAojcGFuZGVyKHNwbGl0LmNlbGwgPSA0MCwgc3BsaXQudGFibGUgPSBJbmYsIHJvdW5kID0gMykKYGBgCgokfiQKCiMgTWFsZSBmaXRuZXNzCgokfiQKClRvIGVzdGltYXRlIHRoZSBmaXRuZXNzIG9mIG1hbGVzIGNhcnJ5aW5nIGVhY2ggb2YgdGhlIHRocmVlIGNocm9tb3NvbWUgdHlwZXMsIHdlIGNvbmR1Y3RlZCBhbiBleHBlcmltZW50IHZlcnkgc2ltaWxhciB0byB0aGUgZmVtYWxlIGZpdG5lc3MgYXNzYXkuIEhvd2V2ZXIsIGJlY2F1c2UgbWFsZSBmaXRuZXNzIGhhcyBzdHJvbmdlciBjb3ZhcmlhbmNlIHdpdGggZmVydGlsaXNhdGlvbiBldmVudHMgdGhhbiBkb2VzIGZlbWFsZSBmaXRuZXNzLCB3ZSBjb25kdWN0ZWQgdGhlIG1hbGUgZml0bmVzcyBhc3NheSB3aXRoIGEgMToyIHNleCByYXRpbyAoZmVtYWxlOm1hbGUpIHJhdGhlciB0aGFuIHRoZSAxOjEgcmF0aW8gdXNlZCBpbiB0aGUgZmVtYWxlIGFzc2F5LiBUaGlzIGluY3JlYXNlcyB0aGUgc3RyZW5ndGggb2Ygc2V4dWFsIHNlbGVjdGlvbiBhbmQgaXMgYSBtb3JlIGFwcHJvcHJpYXRlIHdheSB0byBleHBvc2UgZGlmZmVyZW5jZXMgaW4gZml0bmVzcyBiZXR3ZWVuIGdyb3VwcyBvZiBtYWxlcy4gQXMgd2l0aCB0aGUgZmVtYWxlcywgd2UgY2FsY3VsYXRlZCBmaXRuZXNzIGFzIHRoZSBwcm9wb3J0aW9uIG9mIHJlZC1leWVkIG9mZnNwcmluZyBpbiB0aGUgdmlhbC4gCgpgYGB7cn0KCm1hbGVfZml0bmVzc19tb2RlbCA8LQogIGJybShUb3RhbF9yZWRfb2Zmc3ByaW5nIHwgdmludChUb3RhbF9vZmZzcHJpbmcpIH4gMSArIEluaGVyaXRhbmNlX3RyZWF0bWVudCArIEJsb2NrICsgR0ZQICsgKDF8UG9wdWxhdGlvbikgKyAoMXxSZWFyaW5nX3ZpYWwpLAogICAgICBkYXRhID0gbWFsZV9maXRuZXNzLCBmYW1pbHkgPSBiZXRhX2Jpbm9taWFsMiwgCiAgICAgIHByaW9yID0gYyhwcmlvcihub3JtYWwoMCwgMSksIGNsYXNzID0gSW50ZXJjZXB0KSwKICAgICAgICAgICAgICAgIHByaW9yKG5vcm1hbCgwLCAxLjUpLCBjbGFzcyA9IGIpLAogICAgICAgICAgICAgICAgcHJpb3IoZXhwb25lbnRpYWwoMSksIGNsYXNzID0gcGhpKSksCiAgICAgIGl0ZXIgPSA0MDAwLCB3YXJtdXAgPSAyMDAwLCBjaGFpbnMgPSA0LCBjb3JlcyA9IDQsCiAgICAgIGNvbnRyb2wgPSBsaXN0KGFkYXB0X2RlbHRhID0gMC45NSwgbWF4X3RyZWVkZXB0aCA9IDEwKSwKICAgICAgc2VlZCA9IDIsIHN0YW52YXJzID0gc3RhbnZhcnMsIGZpbGUgPSAiRml0cy9tYWxlX2ZpdG5lc3MubW9kZWwiKQoKCmZpeGVmKG1hbGVfZml0bmVzc19tb2RlbCkgJT4lIAogIGthYmxlKGRpZ2l0cyA9IDMpICU+JSAKICBrYWJsZV9zdHlsaW5nKCkKYGBgCgpgYGB7ciwgaW5jbHVkZT1GQUxTRX0KZXhwb3NlX2Z1bmN0aW9ucyhtYWxlX2ZpdG5lc3NfbW9kZWwsIHZlY3Rvcml6ZSA9IFRSVUUpCmBgYAoKUnVuIExPTyB0byBzZWUgaWYgd2UndmUgZWZmZWN0aXZlbHkgbW9kZWxsZWQgb3ZlciBkaXNwZXJzaW9uLgoKYGBge3J9CgptYWxlX2ZpdG5lc3NfbW9kZWwgPC0gYWRkX2NyaXRlcmlvbihtYWxlX2ZpdG5lc3NfbW9kZWwsIGNyaXRlcmlvbiA9ICJsb28iLCBmaWxlID0gIkZpdHMvbWFsZV9maXRuZXNzLm1vZGVsIikKCmxvbyhtYWxlX2ZpdG5lc3NfbW9kZWwpCgpgYGAKClRoZXJlIGlzIG9uZSBwb2ludCBoYXZpbmcgYSBsYXJnZSBlZmZlY3Qgb24gdGhlIHBvc3Rlcmlvci4gVXBvbiBpbnNwZWN0aW9uLCB0aGlzIGRhdGEgcG9pbnQgaXMgbm90IGFuIHVucmVhc29uYWJsZSBvbmUgYW5kIHRoZXJlIGlzIG5vIGNhdXNlIHRvIHJlbW92ZSBpdCBmcm9tIHRoZSBkYXRhc2V0LiBJdCBhbHNvIGRvZXMgbm90IGNoYW5nZSB0aGUgY2F1c2FsIGVmZmVjdCBvZiBpbmhlcml0YW5jZSB0cmVhdG1lbnQgb24gbWFsZSBmaXRuZXNzLgoKQ29uZHVjdCB0aGUgcG9zdGVyaW9yIHByZWRpY3RpdmUgY2hlY2suLi4KCmBgYHtyfQpwcF9jaGVjayhtYWxlX2ZpdG5lc3NfbW9kZWwsIHR5cGUgPSAiaGlzdCIsIG5kcmF3cyA9IDExLCBiaW53aWR0aCA9IDEwKSArCiAgdGhlbWVfbWluaW1hbCgpICsKICB0aGVtZShwYW5lbC5iYWNrZ3JvdW5kID0gZWxlbWVudF9ibGFuaygpKQpgYGAKCiMjIERlcml2ZSBlc3RpbWF0ZXMgZnJvbSBwb3N0ZXJpb3IKCkdldCBwcmVkaWN0aW9ucyBmcm9tIHRoZSBtb2RlbCBhbmQgcHJlc2VudCB0aGVtIGluIGEgVGFibGUKCmBgYHtyfQoKIyBwcmVkaWN0aW9ucyBmb3IgYmxvY2sgMSwgd2l0aCBVQkkgR0ZQCgpuZXdfZGF0YSA8LSB0aWJibGUoSW5oZXJpdGFuY2VfdHJlYXRtZW50ID0gbWFsZV9maXRuZXNzJEluaGVyaXRhbmNlX3RyZWF0bWVudCkgJT4lIAogIGRpc3RpbmN0KEluaGVyaXRhbmNlX3RyZWF0bWVudCkgJT4lIAogIG11dGF0ZShQb3B1bGF0aW9uID0gMSwKICAgICAgICAgQmxvY2sgPSAxLAogICAgICAgICBSZWFyaW5nX3ZpYWwgPSAxLAogICAgICAgICBHRlAgPSAiVUJJIiwKICAgICAgICAgVG90YWxfb2Zmc3ByaW5nID0gMSkKCnByZWRpY3Rpb25zX21hbGUgPC0gZml0dGVkKG1hbGVfZml0bmVzc19tb2RlbCwgbmV3ZGF0YSA9IG5ld19kYXRhKQoKcHJlZGljdGlvbnNfbWFsZSA8LSBjYmluZChuZXdfZGF0YSwgcHJlZGljdGlvbnNfbWFsZSkKCgp0YWJsZTEgPC0KICBwcmVkaWN0aW9uc19tYWxlICU+JSAKICBzZWxlY3QoLWMoUG9wdWxhdGlvbiwgUmVhcmluZ192aWFsLCBHRlAsIFRvdGFsX29mZnNwcmluZykpICU+JQogIGFycmFuZ2UoQmxvY2spICU+JSAKICBwYW5kZXIoc3BsaXQuY2VsbCA9IDQwLCBzcGxpdC50YWJsZSA9IEluZiwgcm91bmQgPSAzKQoKZHJhd3NfbSA8LSBhc19kcmF3c19kZihtYWxlX2ZpdG5lc3NfbW9kZWwpCgojIHByZWRpY3Rpb25zIGF2ZXJhZ2VkIG92ZXIgbWVkaWF0b3IgdmFyaWFibGVzCgpkcmF3c19tYWxlIDwtCiAgZHJhd3NfbSAgJT4lIAogIG11dGF0ZShgRmVtYWxlLWxpbWl0ZWRgID0gaW52X2xvZ2l0X3NjYWxlZChiX0ludGVyY2VwdCArIGJfSW5oZXJpdGFuY2VfdHJlYXRtZW50RmVtYWxlX2xpbWl0ZWQpLAogICAgICAgICBgTWFsZS1saW1pdGVkYCA9IGludl9sb2dpdF9zY2FsZWQoYl9JbnRlcmNlcHQgKyBiX0luaGVyaXRhbmNlX3RyZWF0bWVudE1hbGVfbGltaXRlZCksCiAgICAgICAgIENvbnRyb2wgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0KSkgJT4lIAogIHNlbGVjdChDb250cm9sLCBgRmVtYWxlLWxpbWl0ZWRgLCBgTWFsZS1saW1pdGVkYCkgJT4lIAogICAgcGl2b3RfbG9uZ2VyKGNvbHMgPSBjKENvbnRyb2wsIGBGZW1hbGUtbGltaXRlZGAsIGBNYWxlLWxpbWl0ZWRgKSwKICAgICAgICAgICAgICAgICBuYW1lc190byA9ICJJbmhlcml0YW5jZV90cmVhdG1lbnQiKSAlPiUgCiAgcmVuYW1lKHByb3BfZm9jYWxfb2Zmc3ByaW5nID0gdmFsdWUpCgpkcmF3c19kaWZmX20gPC0gZHJhd3NfbSAlPiUgCiAgbXV0YXRlKGBGZW1hbGUtbGltaXRlZGAgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0ICsgYl9Jbmhlcml0YW5jZV90cmVhdG1lbnRGZW1hbGVfbGltaXRlZCksCiAgICAgICAgIGBNYWxlLWxpbWl0ZWRgID0gaW52X2xvZ2l0X3NjYWxlZChiX0ludGVyY2VwdCArIGJfSW5oZXJpdGFuY2VfdHJlYXRtZW50TWFsZV9saW1pdGVkKSwKICAgICAgICAgQ29udHJvbCA9IGludl9sb2dpdF9zY2FsZWQoYl9JbnRlcmNlcHQpKSAlPiUKICBtdXRhdGUoYEZlbWFsZSAtIENvbnRyb2xgID0gYEZlbWFsZS1saW1pdGVkYCAtIENvbnRyb2wsCiAgICAgICAgIGBNYWxlIC0gQ29udHJvbGAgPSBgTWFsZS1saW1pdGVkYCAtIENvbnRyb2wsCiAgICAgICAgIGBGZW1hbGUgLSBNYWxlYCA9IGBGZW1hbGUtbGltaXRlZGAgLSBgTWFsZS1saW1pdGVkYCkgJT4lIAogIHNlbGVjdChgRmVtYWxlIC0gQ29udHJvbGAsIGBNYWxlIC0gQ29udHJvbGAsIGBGZW1hbGUgLSBNYWxlYCkKCiMgYWN0dWFsIFRhYmxlIDEKCmRyYXdzX21hbGUgJT4lIAogIGdyb3VwX2J5KEluaGVyaXRhbmNlX3RyZWF0bWVudCkgJT4lIAogIHN1bW1hcmlzZShgRXN0aW1hdGVkIHByb3AuIG9mIG9mZnNwcmluZyBzaXJlZGAgPSBtZWFuKHByb3BfZm9jYWxfb2Zmc3ByaW5nKSwKICAgICAgICAgICAgYDIuNSVgID0gcXVhbnRpbGUocHJvcF9mb2NhbF9vZmZzcHJpbmcsIHByb2JzID0gMC4wMjUpLAogICAgICAgICAgICBgOTcuNSVgID0gcXVhbnRpbGUocHJvcF9mb2NhbF9vZmZzcHJpbmcsIHByb2JzID0gMC45NzUpKSAlPiUgCiAgcGFuZGVyKHNwbGl0LmNlbGwgPSA0MCwgc3BsaXQudGFibGUgPSBJbmYsIHJvdW5kID0gMykKCiMgbm93IGZpbmQgdGhlIGRpZmZlcmVuY2VzIGJldHdlZW4gdGhlIGNvbnRyb2wgYW5kIHRoZSBzZXgtbGltaXRlZCBFdm9sdXRpb25fdHJlYXRtZW50cwoKIyB0aGUgaW52X2xvZ2l0X3NjYWxlZCgpIGZ1bmN0aW9uIGNvbnZlcnRzIHRoZSBwb3N0ZXJpb3IgZHJhd3Mgb250byB0aGUgcmVzcG9uc2Ugc2NhbGUgCgpwcm9wX3RhYmxlX21hbGUgPC0gCiAgZHJhd3NfbSAlPiUgCiAgbXV0YXRlKHBfY29udHJvbCA9ICBpbnZfbG9naXRfc2NhbGVkKGJfSW50ZXJjZXB0KSwKICAgICAgICAgcF9mZW1hbGUgPSBpbnZfbG9naXRfc2NhbGVkKGJfSW5oZXJpdGFuY2VfdHJlYXRtZW50RmVtYWxlX2xpbWl0ZWQgKyBiX0ludGVyY2VwdCksCiAgICAgICAgIHBfbWFsZSA9IGludl9sb2dpdF9zY2FsZWQoYl9Jbmhlcml0YW5jZV90cmVhdG1lbnRNYWxlX2xpbWl0ZWQgKyBiX0ludGVyY2VwdCksCiAgICAgICAgIGBGZW1hbGUtbGltaXRlZGAgPSBwX2ZlbWFsZSAvIHBfY29udHJvbCwKICAgICAgICAgYE1hbGUtbGltaXRlZGAgPSBwX21hbGUgLyBwX2NvbnRyb2wpICU+JSAKICBnYXRoZXIoa2V5ID0gYGRpZmZlcmVuY2UgY29tcGFyaXNvbmAsIHZhbHVlID0gYCUgZGlmZmVyZW5jZWApICU+JSAKICBmaWx0ZXIoYGRpZmZlcmVuY2UgY29tcGFyaXNvbmAgPT0gYygiRmVtYWxlLWxpbWl0ZWQiLCAiTWFsZS1saW1pdGVkIikpICU+JSAKICBncm91cF9ieShgZGlmZmVyZW5jZSBjb21wYXJpc29uYCkgICU+JSAKICBzdW1tYXJpc2UoYE1lYW4gcHJvcG9ydGlvbiBvZiBvZmZzcHJpbmcgc2lyZWQgcmVsYXRpdmUgdG8gY29udHJvbGAgID0gbWVhbihgJSBkaWZmZXJlbmNlYCksCiAgICAgICAgICAgIGAyLjUlYCA9IHF1YW50aWxlKGAlIGRpZmZlcmVuY2VgLCBwcm9icyA9IDAuMDI1KSwKICAgICAgICAgICAgYDk3LjUlYCA9IHF1YW50aWxlKGAlIGRpZmZlcmVuY2VgLCBwcm9icyA9IDAuOTc1KSkgJT4lIAogIHJlbmFtZShgSW5oZXJpdGFuY2UgdHJlYXRtZW50YCA9IGBkaWZmZXJlbmNlIGNvbXBhcmlzb25gKSAjJT4lIAogICNwYW5kZXIoc3BsaXQuY2VsbCA9IDQwLCBzcGxpdC50YWJsZSA9IEluZiwgcm91bmQgPSAzKQpgYGAKCiMgQnVpbGRpbmcgRmlndXJlIDIKCmBgYHtyLCBmaWcuaGVpZ2h0PTgsIGZpZy53aWR0aD04fQoKIyBmZW1hbGUgcGxvdHMKCmZfMSA8LQogIGRyYXdzX2ZlbWFsZSAlPiUgCiAgbXV0YXRlKEluaGVyaXRhbmNlX3RyZWF0bWVudCA9IGZjdF9yZWxldmVsKEluaGVyaXRhbmNlX3RyZWF0bWVudCwgIkZlbWFsZS1saW1pdGVkIiwgIkNvbnRyb2wiLCAiTWFsZS1saW1pdGVkIikpICU+JSAKICBnZ3Bsb3QoYWVzKEluaGVyaXRhbmNlX3RyZWF0bWVudCwgcHJvcF9mb2NhbF9vZmZzcHJpbmcpKSArIAogIHN0YXRfaGFsZmV5ZShhZXMoZmlsbCA9IEluaGVyaXRhbmNlX3RyZWF0bWVudCksIC53aWR0aCA9IGMoMC42NiwgMC45NSksIGFscGhhID0gMSwKICAgICAgICAgICAgICAgcG9pbnRfaW50ZXJ2YWwgPSAibWVhbl9xaSIsIHBvaW50X2ZpbGwgPSAid2hpdGUiLAogICAgICAgICAgICAgICBzaGFwZSA9IDIxLCBwb2ludF9zaXplID0gMywgc3Ryb2tlID0gMS41KSArICMgd2lkdGggaW5kaWNhdGVzIHRoZSB1bmNlcnRhaW50eSBpbnRlcnZhbHM6IHdlIGhhdmUgNjYlIGFuZCA5NSUgaW50ZXJ2YWxzCiAgc2NhbGVfZmlsbF9tYW51YWwodmFsdWVzID0gbWV0LmJyZXdlcigiSGlyb3NoaWdlIiwgMykpICsKICBjb29yZF9mbGlwKCkgKwogIHhsYWIoIkluaGVyaXRhbmNlIHRyZWF0bWVudCIpICsKICB5bGFiKCJGZW1hbGUgZml0bmVzc1xuKHByb3AuIG9mZnNwcmluZyBwcm9kdWNlZCkiKSArCiAgdGhlbWVfYncoKSArIAogIHRoZW1lKGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIiwKICAgICAgICBwYW5lbC5ncmlkLm1pbm9yID0gZWxlbWVudF9ibGFuaygpKQoKZl8yIDwtCiAgZHJhd3NfZGlmZiAlPiUgCiAgZ2F0aGVyKGtleSA9IHBhcmFtZXRlciwgdmFsdWUgPSBgRml0bmVzcyBkaWZmZXJlbmNlYCkgJT4lIAogIGFzX3RpYmJsZSgpICU+JSAgIAoKICBnZ3Bsb3QoYWVzKHBhcmFtZXRlciwgYEZpdG5lc3MgZGlmZmVyZW5jZWApKSArIAogIHN0YXRfaGFsZmV5ZSgud2lkdGggPSBjKDAuNjYsIDAuOTUpLCBhbHBoYSA9IDAuOSwgcG9pbnRfaW50ZXJ2YWwgPSAibWVhbl9xaSIsCiAgICAgICAgICAgICAgIHNsYWJfZmlsbCA9IG1ldC5icmV3ZXIoIkhpcm9zaGlnZSIpWzFdLAogICAgICAgICAgICAgICBzaGFwZSA9IDIxLCBwb2ludF9zaXplID0gMywgc3Ryb2tlID0gMS41LAogICAgICAgICAgICAgICBwb2ludF9maWxsID0gIndoaXRlIikgKyAjIHdpZHRoIGluZGljYXRlcyB0aGUgdW5jZXJ0YWludHkgaW50ZXJ2YWxzOiBoZXJlIHdlIGhhdmUgNjYlIGFuZCA5NSUgaW50ZXJ2YWxzCiAgY29vcmRfZmxpcCgpICsKICBnZW9tX2hsaW5lKHlpbnRlcmNlcHQgPSAwLCBsaW5ldHlwZSA9IDIpICsKICAjc2NhbGVfeV9jb250aW51b3VzKGJyZWFrcyA9IGMoLCAwLCAxKSkgKwogIHhsYWIoIlRyZWF0bWVudCBjb250cmFzdCIpICsKICB5bGFiKCJGZW1hbGUgZml0bmVzcyBkaWZmZXJlbmNlXG4ocHJvcC4gb2Zmc3ByaW5nIHByb2R1Y2VkKSIpICsKICB0aGVtZV9idygpICsgCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uID0gIm5vbmUiLAogICAgICAgIHBhbmVsLmdyaWQubWlub3IgPSBlbGVtZW50X2JsYW5rKCkpCgojIG1hbGUgcGxvdHMKCmZfMyA8LQogIGRyYXdzX21hbGUgJT4lIAogIG11dGF0ZShJbmhlcml0YW5jZV90cmVhdG1lbnQgPSBmY3RfcmVsZXZlbChJbmhlcml0YW5jZV90cmVhdG1lbnQsICJGZW1hbGUtbGltaXRlZCIsICJDb250cm9sIiwgIk1hbGUtbGltaXRlZCIpKSAlPiUgCiAgZ2dwbG90KGFlcyhJbmhlcml0YW5jZV90cmVhdG1lbnQsIHByb3BfZm9jYWxfb2Zmc3ByaW5nKSkgKyAKICAgc3RhdF9oYWxmZXllKGFlcyhmaWxsID0gSW5oZXJpdGFuY2VfdHJlYXRtZW50KSwgLndpZHRoID0gYygwLjY2LCAwLjk1KSwgYWxwaGEgPSAxLAogICAgICAgICAgICAgICBwb2ludF9pbnRlcnZhbCA9ICJtZWFuX3FpIiwgcG9pbnRfZmlsbCA9ICJ3aGl0ZSIsCiAgICAgICAgICAgICAgIHNoYXBlID0gMjEsIHBvaW50X3NpemUgPSAzLCBzdHJva2UgPSAxLjUpICsgIyB3aWR0aCBpbmRpY2F0ZXMgdGhlIHVuY2VydGFpbnR5IGludGVydmFsczogaGVyZSB3ZSBoYXZlIDY2JSBhbmQgOTUlIGludGVydmFscwogIHNjYWxlX2ZpbGxfbWFudWFsKHZhbHVlcyA9IG1ldC5icmV3ZXIoIkhpcm9zaGlnZSIsIDMpKSArCiAgY29vcmRfZmxpcCgpICsKICB4bGFiKCJJbmhlcml0YW5jZSB0cmVhdG1lbnQiKSArCiAgeWxhYigiTWFsZSBmaXRuZXNzXG4ocHJvcC4gb2Zmc3ByaW5nIHByb2R1Y2VkKSIpICsKICB0aGVtZV9idygpICsgCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uID0gIm5vbmUiLAogICAgICAgIHBhbmVsLmdyaWQubWlub3IgPSBlbGVtZW50X2JsYW5rKCkpCgpmXzQgPC0KICBkcmF3c19kaWZmX20gJT4lCiAgZ2F0aGVyKGtleSA9IHBhcmFtZXRlciwgdmFsdWUgPSBgRml0bmVzcyBkaWZmZXJlbmNlYCkgJT4lIAogIGFzX3RpYmJsZSgpICU+JSAKICBnZ3Bsb3QoYWVzKHBhcmFtZXRlciwgYEZpdG5lc3MgZGlmZmVyZW5jZWApKSArIAogIHN0YXRfaGFsZmV5ZSgud2lkdGggPSBjKDAuNjYsIDAuOTUpLCBhbHBoYSA9IDAuOSwgcG9pbnRfaW50ZXJ2YWwgPSAibWVhbl9xaSIsCiAgICAgICAgICAgICAgIHNsYWJfZmlsbCA9IG1ldC5icmV3ZXIoIkhpcm9zaGlnZSIpWzFdLAogICAgICAgICAgICAgICBzaGFwZSA9IDIxLCBwb2ludF9zaXplID0gMywgc3Ryb2tlID0gMS41LAogICAgICAgICAgICAgICBwb2ludF9maWxsID0gIndoaXRlIikgKyAjIHdpZHRoIGluZGljYXRlcyB0aGUgdW5jZXJ0YWludHkgaW50ZXJ2YWxzOiBoZXJlIHdlIGhhdmUgNjYlIGFuZCA5NSUgaW50ZXJ2YWxzCiAgc2NhbGVfZmlsbF9tYW51YWwodmFsdWVzID0gbWV0LmJyZXdlcigiSG9rdXNhaTMiLCAzKSkgKwogIGNvb3JkX2ZsaXAoKSArCiAgZ2VvbV9obGluZSh5aW50ZXJjZXB0ID0gMCwgbGluZXR5cGUgPSAyKSArCiAgc2NhbGVfeV9jb250aW51b3VzKGJyZWFrcyA9IGMoLTAuMiwgLTAuMSwgMCwgMC4xLCAwLjIpKSArCiAgeGxhYigiVHJlYXRtZW50IGNvbnRyYXN0IikgKwogIHlsYWIoIk1hbGUgZml0bmVzcyBkaWZmZXJlbmNlXG4ocHJvcC4gb2Zmc3ByaW5nIHNpcmVkKSIpICsKICB0aGVtZV9idygpICsgCiAgdGhlbWUobGVnZW5kLnBvc2l0aW9uID0gIm5vbmUiLAogICAgICAgIHBhbmVsLmdyaWQubWlub3IgPSBlbGVtZW50X2JsYW5rKCkpCgoKKGZfMSArIGZfMikgLyhmXzMgKyBmXzQpICsgCiAgcGxvdF9hbm5vdGF0aW9uKHRhZ19sZXZlbHMgPSAnYScpCgpgYGAKCioqRmlndXJlIDIqKjogKiphKiogc2hvd3MgdGhlIGVzdGltYXRlZCBkaXN0cmlidXRpb24gb2YgdGhlIG1lYW4gZm9yIGZlbWFsZSBmaXRuZXNzIGZvciBmbGllcyBjYXJyeWluZyBhdXRvc29tZXMgdGhhdCBoYWQgcHJldmlvdXNseSBleHBlcmllbmNlZCB1bmNvbnN0cmFpbmVkIGluaGVyaXRhbmNlIChjb250cm9sKSwgZmVtYWxlLWxpbWl0ZWQgaW5oZXJpdGFuY2Ugb3IgbWFsZS1saW1pdGVkIGluaGVyaXRhbmNlLiAqKmIqKiBzaG93cyB0aGUgZGlmZmVyZW5jZSBjb250cmFzdCBpbiBmZW1hbGUgZml0bmVzcyBiZXR3ZWVuIGVhY2ggb2YgdGhlIHRocmVlIGluaGVyaXRhbmNlIHRyZWF0bWVudHMuIFRoaXMgZGlmZmVyZW5jZSBpcyBvbiB0aGUgcHJvcG9ydGlvbiBzY2FsZSwgd2hlcmUgYSB2YWx1ZSBvZiAwLjEgaW5kaWNhdGVzIHRoYXQgZmVtYWxlcyBvZiBhIGdpdmVuIGluaGVyaXRhbmNlIHRyZWF0bWVudCBwcm9kdWNlIDEwIG1vcmUgb2Zmc3ByaW5nIHBlciBldmVyeSAxMDAgd2hlbiBjb2hhYml0aW5nIHdpdGggX2J3XyBjb21wZXRpdG9yIGZlbWFsZXMuICoqYyoqIGFuZCAqKmQqKiBkZXBpY3QgdGhlIHNhbWUgdGhpbmdzIGFzICoqYSoqIGFuZCAqKmIqKiwgZXhjZXB0IGZvciBtYWxlIGZpdG5lc3MuCgo=